V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
V2EX 提问指南
kehr
V2EX  ›  问与答

在 URL 中放 # 是出于什么考虑?

  •  2
     
  •   kehr · 2015-07-04 20:05:00 +08:00 · 5905 次点击
    这是一个创建于 3441 天前的主题,其中的信息可能已经有所发展或是发生改变。

    今天发现网页版网易云音乐分享歌单 http://music.163.com/#/share/35255916/90382499
    路径里有个#,之前也遇到过类似的情况。网上搜了一圈,都被导向锚点的解释去了,显然不是我想要的答案。

    于是我用 Tornado 测试了一下:

    class Application(tornado.web.Application):
    
        def __init__(self):
            """"""
            handlers = [
                (r"/", IndexHandler),
                (r"/#/test", TestHandler),
    
    class TestHandler(BaseHandler):
        def get(self):
            self.write("可以访问!")
    

    Server 地址是: http://localhost:8090

    结果如下:
    1. 访问 http://localhost:8090/#/test 返回的是首页
    2. 修改代码

    class Application(tornado.web.Application):
    
        def __init__(self):
            """"""
            handlers = [
                (r"/", IndexHandler),
                (r"/test", TestHandler),
    

    访问 http://localhost:8090/test,确认服务正常,可以返回预期页面。

    那么很显然了:# 放在 URL 中虽然看起来像是一级路径,但还是起到锚点的作用。浏览器会自动把 # 及其以后的整体部分识别为锚点(猜测)。

    随之问题来了:

    为什么现在开发要用采用这种方案呢?是考虑抓取问题么?

    这个问题困扰我一段时间了,公司内部也有两个平台是这么做的(显然和抓取没毛线关系)。问了一圈貌似也没人知道。

    求指导 ಥ_ಥ

    21 条回复    2015-07-04 23:53:53 +08:00
    TakanashiAzusa
        1
    TakanashiAzusa  
       2015-07-04 20:08:09 +08:00   ❤️ 3
    利用的是html5的history api,这个阮一峰有文章讲过(虽然我还没吃透。)
    主要应该是出于用户体验的考虑
    http://www.ruanyifeng.com/blog/2011/03/url_hash.html
    MForever78
        2
    MForever78  
       2015-07-04 20:08:32 +08:00
    前端路由而已。
    nealnote
        3
    nealnote  
       2015-07-04 20:19:13 +08:00   ❤️ 3
    理解url标准或者说规范 rfc 1808
    http://www.w3.org/Addressing/rfc1808.txt
    # 后面是页面内标识符,并不会提交给服务器

    这里被用作web app 的路由,打开页面加载一次,其他操作大部分都是页面局部刷新了,不用重新去服务器获取整个页面所有元素
    kehr
        4
    kehr  
    OP
       2015-07-04 20:20:43 +08:00
    @TakanashiAzusa Thanks

    和不在URL里用 # 感觉起来差不多,还增加了处理 HTTP 请求的复杂性。
    但是这么做增加的是哪方面的用户体验呢?
    gongpeione
        5
    gongpeione  
       2015-07-04 20:24:19 +08:00
    前端路由+1
    切换#后面的内容页面不会刷新
    然后js可以通过window.location.hash获取#后面内容 然后就可以ajax之类的了
    Tink
        6
    Tink  
       2015-07-04 20:25:40 +08:00 via iPhone
    前端路由
    TakanashiAzusa
        7
    TakanashiAzusa  
       2015-07-04 20:26:21 +08:00   ❤️ 1
    @kehr 这样可以通过ajax提交,页面就不需要跳转了,所谓的单页面应用。另外不跳转的话不需要刷新服务器资源,也可以减少服务器压力。由于这个我不是太怎么了解,就不多说了,给你两个链接参考下。
    http://codecampo.com/topics/84
    http://www.zhihu.com/question/26907726
    kehr
        8
    kehr  
    OP
       2015-07-04 20:27:27 +08:00
    @nealnote 谢谢!我有点明白了。

    这种方式全部 Ajax 也能做。用 # 再结合 Ajax 做也是个不错的方案。

    ![]( )
    weizhenye
        9
    weizhenye  
       2015-07-04 20:30:06 +08:00   ❤️ 1
    个人猜测. 网易音乐要做到切换页面但不中断播放, 可以采用 Pjax. 但又要兼容不支持 History API 的浏览器, 于是就用 # 了
    hellogmh
        10
    hellogmh  
       2015-07-04 20:35:06 +08:00   ❤️ 2
    F12看music.163.com的JS代码,注释里面写得很清楚
    //获取URL path 之后的所有内容,并将/#/替换成/m/使之成为path的一部分
    ksc010
        11
    ksc010  
       2015-07-04 20:49:14 +08:00
    这样做的话可以保证页面不刷新
    url有变化
    并且有历史记录(可前进倒退)
    前端js可感知
    jasontse
        12
    jasontse  
       2015-07-04 20:57:44 +08:00 via Android
    wsph123
        13
    wsph123  
       2015-07-04 21:21:05 +08:00
    前端路由 ,hash 可以做到兼容 IE6+
    min
        14
    min  
       2015-07-04 21:43:53 +08:00 via iPhone
    spa 页内导航
    learnshare
        15
    learnshare  
       2015-07-04 22:08:16 +08:00   ❤️ 1
    单页应用使用 URL 的一种方式,1 是可以确保历史记录正确,2 是可以在 URL 中保留一些参数,供 JS 调用
    也有一些不会用 #,两种还是有一些差别的

    Angular.js 相关的介绍 https://docs.angularjs.org/guide/$location
    kn007
        16
    kn007  
       2015-07-04 22:40:04 +08:00
    mark
    Phariel
        17
    Phariel  
       2015-07-04 22:43:49 +08:00
    我厂就使用此方法,前端路由,单页面应用,可记住所有状态,history back可用。
    sneezry
        18
    sneezry  
       2015-07-04 23:04:53 +08:00
    单页面应用设计,Single Page Application,这样页面渲染可以交给前端来完成,后端只负责数据传输,通常用JSON和XML进行数据格式化
    Biwood
        19
    Biwood  
       2015-07-04 23:15:13 +08:00
    网易云音乐这个是非常特殊的单页应用(SPA),他们不是用 AJAX 而是用 iframe,他们的页面内容全部都是嵌套在一个 iframe 里面,只有页面底下的播放器在 iframe 之外,这是为了使得用户浏览内容的时候不会刷新正在播放的歌曲。

    至于#后面的部分数据,其实就是 iframe 指向的地址,他们监听了 hash 的变化,每次 hash 发生变化时就把地址赋值给 iframe 的 src,以实现页面的跳转。你可以右键查看他们的页面源代码,直接就能找到那段监听 hash 值变化的代码。
    Biwood
        20
    Biwood  
       2015-07-04 23:22:12 +08:00
    网易云音乐的 hash 的使用属于特殊案例,而一般的锚点都是用来指向页面上的某一个片段的,这样能够精确定位到页面上的某一部分内容,比如很多技术文档的二级标题前面都有一个可以点击的链条图标,这个就是为了方便用户复制链接并分享该片段,当别人点击这个链接时可以在打开网页后直接跳到该片段,而不是停留在网页的顶部,类似这种链接: https://help.github.com/articles/set-up-git/#setting-up-git
    dallaslu
        21
    dallaslu  
       2015-07-04 23:53:53 +08:00
    如果把网易云音乐的网址中的 # 去掉,是可以访问的,不过会被重新定位到带 # 的链接上。可以访问的页面是单个歌曲的信息,带 # 号的页面是一个播放器框架,使用 iframe 引用了单曲页。

    一个播放器,是典型的单页应用,所以用这种方案会有楼上所说的各种好处。

    有人提到 history api,可以先去了解一下 PJAX。进一步可以了解一下类似 twitter 中在 url 里加入 !# 的原因。
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   5747 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 34ms · UTC 03:14 · PVG 11:14 · LAX 19:14 · JFK 22:14
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.