如何在Ruby on Rails中获得当前的绝对URL?


Answers:


1442

对于Rails 3.2或Rails 4+

您应该使用request.original_url获取当前URL。

该方法记录在original_url方法中,但是如果您很好奇,则实现为:

def original_url
  base_url + original_fullpath
end

对于Rails 3:

您可以编写"#{request.protocol}#{request.host_with_port}#{request.fullpath}",因为request.url现在已弃用。


对于Rails 2:

您可以写request.url而不是request.request_uri。这将协议(通常为http://)与主机以及request_uri结合在一起,以提供完整的地址。


31
正如其他用户指出的:DEPRECATION警告:不建议使用#request_uri。请改用fullpath
giladbu 2011年

9
@giladbu fullpath不包含协议/域/端口!这不是绝对网址!
艾伦·H。

37
"http://#{request.host+request.fullpath}"(如果端口很重要的话)还是可以的?"http://#{request.host}:#{request.port+request.fullpath}"
Nilloc

7
如果重要的港口,这一项是正确的: "http://#{request.host}:#{request.port}#{request.fullpath}"
Sucrenoir 2012年

3
您可以指向request.url已弃用的索赔的参考吗?提议的解决方案只是说出request.url已经做的事情的很长的路要走。实现只是协议+ host_with_port + fullpath(github.com/rails/rails/blob/…
mhartl

134

我认为Ruby on Rails 3.0方法现在可以使用了request.fullpath


13
fullpath不包括域
卢拉拉

我很高兴看到了这个提示,因为我实际上正在寻找如何不包括域。
杰克

121

你可以用 url_for(only_path: false)


在我的情况(有点特殊的情况)中,这几乎正是我想要的。我只是将选项更改为true,并获得了当前页面的网址,没有选项。谢谢:)
Spiralis

@David不在视图中,它不是。但无论如何都不应在那儿使用它=)
Lyuben Todorov

就我而言,我想更改主机名,但保留其他所有内容。我发现url_for(host:'www.newdomain.com')对我来说是最有效的解决方案。IMO,它是一个更强大的解决方案,因为在所有版本的导轨上都相同。
PeppyHeppy 2012年

1
仅供参考:如果同一资源有多个路径,则此方法将无效。
thekingoftruth 2014年

68

弃用警告:不建议使用#request_uri。请改用fullpath。


4
请参阅有关答案stackoverflow.com/a/2165727/166279的注释,全路径不包含域。
Nilloc

这条线直接来自撰写本文时的记录,request.uri并且已经在此问题中多次指出,但是...好的,谢谢
ecoologic 2012年

1
@ManishShrivastava:有趣的是,尽管我付出了所有“原始”的努力来回答更复杂的问题,但这种复制粘贴还是给了我最高分,好……总比没有好
生态2014年


52

您可以在ApplicationController中添加此current_url方法以返回当前URL并允许合并其他参数

# https://x.com/y/1?page=1 
# + current_url( :page => 3 )
# = https://x.com/y/1?page=3
def current_url(overwrite={})
    url_for :only_path => false, :params => params.merge(overwrite)
end

用法示例:

current_url --> http://...
current_url(:page=>4) --> http://...&page=4

1
这似乎未在Rails 3.1中定义。
艾伦·H。

1
您可以通过这种方式完成url_for params.merge(:format => "PDF", :only_path => false)
montrealmike 2012年

2
另外,如果您在link_to,则可以完全params.merge跳过使用url_for
montrealmike 2012年

36

对于Ruby on Rails 3:

request.url
request.host_with_port

我启动了一个调试器会话并查询了请求对象:

request.public_methods


28

我需要应用程序URL,但需要有子目录。我用了:

root_url(:only_path => false)


16

我认为request.domain可以工作,但是如果您位于blah.blah.com之类的子目录中怎么办?这样的事情可能会起作用:

<%= request.env["HTTP_HOST"] + page = "/" + request.path_parameters['controller'] + "/" + request.path_parameters['action'] %>

根据您的路径结构更改参数。

希望有帮助!


8
是的,Jaime的答案要好得多,但是如果您想真正地降低效率,可以按照我的方式来做。
詹姆斯M,2010年

14

看起来request_uri在Ruby on Rails 3中已弃用。

Using #request_uri is deprecated. Use fullpath instead.

13

使用Ruby 1.9.3-p194和Ruby on Rails 3.2.6:

如果request.fullpath不适用于您,请尝试request.env [“ HTTP_REFERER”]

这是我下面的故事。

在检测当前URL(在用户浏览器的地址栏中显示)的累积页面时,我遇到了类似的问题,该页面合并了来自不同控制器的信息,例如http://localhost:3002/users/1/history/issues

用户可以切换到不同类型的问题列表。所有这些列表都是通过Ajax从不同的控制器/部分加载的(无需重新加载)。

问题是在列表的每个项目中为后退按钮设置正确的路径,以便后退按钮可以在其自己的页面和累积页面历史记录中正常工作

如果我使用request.fullpath,它将返回上一个JavaScript请求的路径,这绝对不是我要查找的URL。

因此,我使用了request.env [“ HTTP_REFERER”]来存储上次重新加载的请求的URL。

这是部分决定的摘录

- if request.env["HTTP_REFERER"].to_s.scan("history").length > 0
  - back_url = user_history_issue_path(@user, list: "needed_type")
- else
  - back_url = user_needed_type_issue_path(@user)
- remote ||= false
=link_to t("static.back"), back_url, :remote => remote

是的,fullpath会为您提供您请求的URL,而不是您来自的URL ,这也是我所需要的。谢谢你!
Spencer Rathbun 2012年

2
效果很好,正是我所需要的。但是,这应该在单独的问答中。金田很难在这里找到。:/
DDDD 2014年

12

这适用于Ruby on Rails 3.0,并且大多数版本的Ruby on Rails都应支持:

request.env['REQUEST_URI']

11

除了有人说他使用调试器找到他所寻找的内容之外,该线程中的所有建议都没有对我有帮助。

我创建了一些自定义错误页面,而不是标准的404和500,但是request.url/404预期的结尾/non-existing-mumbo-jumbo

我需要使用的是

request.original_url

9

如果相对而言,您的意思是没有域,请查看request.domain


8
(url_for(:only_path => false) == "/" )? root_url : url_for(:only_path => false)

8

您可以使用ruby方法:

:root_url

这将获得带有基本URL的完整路径:

localhost:3000/bla

这是在使用active_model_serializers串行Rails中4工作的唯一解决方案
克里斯·凯拉

你能告诉我当我使用诸如:root_url获取绝对URL之类的东西时如何限制传递给绝对URL的参数吗?假设我使用类似的东西some_method(:products_brand_url, brand: brand, entity_name: "brand")some_method并且定义为`def some_method(route,opts = {})end`我不希望我的路线看起来像- http://localhost:3000/brands/brand_name?&entity_name="brand"。我希望路线看起来像http://localhost:3000/brands/brand_name。我只希望entity_name成为opts哈希的一部分,而不是绝对url的参数。
boddhisattva'2

当然,没有所谓的Ruby方法root_url
smileart '19


6

您可以将任何一个用于rails 3.2:

request.original_url
or
request.env["HTTP_REFERER"]
or
request.env['REQUEST_URI']

我认为它可以在任何地方使用

"#{request.protocol}#{request.host}:#{request.port}#{request.fullpath}"

6

Rails 4.0

您可以使用request.original_url,输出将如以下示例所示

get "/articles?page=2"

request.original_url # => "http://www.example.com/articles?page=2"

4

对于Rails 3.2或Rails 4, 只需采用这种方式即可获得“ request.original_url”参考:原始URL方法

对于Rails 3, 因为request.url已被弃用。我们可以通过级联获得绝对路径

"#{request.protocol}#{request.host_with_port}#{request.fullpath}"

对于Rails 2

request.url

3

如果您想表达具体的意思,就知道需要的路径:

link_to current_path(@resource, :only_path => false), current_path(@resource)



3

获取没有任何查询参数的请求URL。

def current_url_without_parameters
  request.base_url + request.path
end

3

您可以使用

request.original_url 

要么

"#{request.protocol}#{request.host_with_port}" 

获取当前URL。



1

您可以将变量设置为URI.parse(current_url),我在这里还没有看到这个建议,它对我也有效。


0

要获取绝对网址,这意味着 from the root可以这样显示

<%= link_to 'Edit', edit_user_url(user) %>

users_url帮助程序将生成一个包含协议和主机名的URL。users_path帮助器仅生成路径部分。

users_url: http://localhost/users
users_path: /users
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.