I have some links as follow.
http://www.example.com/excel.aspx
http://www.example.com:80/word.aspx
http://www.example.com:80/powerpoint.aspx
http://www.example.com:80/pdf.aspx
http://www.example.com:80/barcode.aspx
http://www.example.com/ocr.aspx
http://www.example.com/email.aspx
http://www.example.com/project.aspx
& I want to rewrite the URLs as following in a single regex pattern or single regex line.
https://www.example.com/excel
https://www.example.com/word
https://www.example.com/powerpoint
https://www.example.com/pdf
https://www.example.com/barcode
https://www.example.com/ocr
https://www.example.com/outlook
https://www.example.com/project
If you check & compare, I have replaced email with outlook in substitution URL.
I can match patterns as follow .*/(\w+).aspx and substitute as https://www.example.com/$1 but I cannot find a way to replace email with outlook. Demo https://regex101.com/r/71huIx/24
Something similar to http://www.rexegg.com/regex-trick-conditional-replacement.html but without a pool or dictionary. However, if the pool or dictionary can be part of regex itself then it will OK. Reason being, I have txt file with rules, where line1 is regex & line2 is a substitution.
Any ideas how can I do that?
Here's an Apache httpd config that should work:
RewriteEngine On
RewriteRule ^/outlook$ https://example.com/email.aspx [P,L]
RewriteRule ^/([^./])/?$ https://example.com/$1.aspx [P,L]
This uses a reverse proxy to serve pages like email.aspx and foobar.aspx when given "outlook" and "foobar" without revealing their extensions to users.
Though it looks like you're trying to go backwards for some reason. In that case, you'd want:
RewriteEngine On
RewriteRule ^/email\.aspx$ https://example.com/outlook [L]
RewriteRule ^/([^.]+)\.aspx$ https://example.com/$1 [L]
Regex conditional expressions cannot perform your task. The structure of a regex conditional is:
(?(condition)yes-pattern|no-pattern)
condition is either
a zero-width assertion (typically a lookahead)
a parenthesized integer, denoting whether that numbered capture has content
a capture group name in angle brackets or single quotes
(R) which is true when evaluated inside a recursion or eval
yes-pattern is a regex to match given the condition is true
no-pattern is an optional regex to match given the condition is false
Therefore, you can't shove new text into the match using a conditional.
Related
I am redirecting certain urls with path to get variables like the following:
localhost2/post/myTitle => localhost2/post.php?title=myTitle
localhost2/post/123 => localhost2/post.php?id=123
So In my htaccess file, I use
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteRule ^post/(\d+) post.php?id=$1
RewriteRule ^post/(.*) post.php?title=$1
</IfModule>
This works no problem. But I want to learn how to write negative of ^post/(\d+), that is ^post/(NEGATE-ONLY-NUMBERS). In other words I want a regex that matches the whole input sting if there is not only numbers after post/. So post/abc, post/a23, post/ab3, post/12c and post/a2c should all pass but not post/123. I refered to this post, which suggest using:
(?!^\d+$)^.+$
I can't use ^post/(?!^\d+$)^.+$, because there can be only one ^ and one $. I don't know what regex anchor specifies first position in a substring. My best guess is
post\/(?!\d++).*
I think (?!\d++), with the ++ would eat all characters followig and check if all are digits. But this fails at post/1ab.
Another guess is:
post\/(?![\d,\/]+$).*
The works the best but it allows: post/3455/X.
Secondly, eventually I need to convert localhost2/post/myTitle/123 => localhost2/post.php?title=myTitle&repeat=123 as well. I ave come up with the following:
^post/(?!\d+($|/))(.+?($|/))(\d+$)?
Note: +? to use lazy quantifier, otherwise multiple slashes will be matched by .
and
^post/(?!\d+($|/))([^/\n\r]+($|/))(\d+$)?
Here I use [^/\n\r] instead of .+?
Patterns inside zero-width assertions like (?!\d++) are non-consuming, they do not "eat" chars, they only check the context while keeping the regex index at the same location as before matching the zero-width assertion pattern.
You can use any of the following:
^post/(?!\d+(?:/|$)).*
^post/(?!\d+(?=/|$)).*
^post/(?!\d+(?![^/])).*
See the regex demo. Details:
^post/ - start of input, post/ literal string
(?!\d+(?=/|$)) - a negative lookahead that fails the match if, immediately to the right of the current location, there are one or more digits followed with / or end of string
.* - the rest of the input.
Do not over complicate things when you can keep things simple by keeping 3 separate rewrite rules and since your query parameters are named differently you will need 3 separate rewrite rules anyway.
Consider:
Options -MultiViews
RewriteEngine On
RewriteRule ^post/(\d+) post.php?id=$1 [L,QSA,NC]
RewriteRule ^post/([^/]+)/(\d+) post.php?title=$1&repeat=$2 [L,QSA,NC]
RewriteRule ^post/([^/]*) post.php?title=$1 [L,QSA,NC]
Take note of Options -MultiViews. If this is not enabled in Apache config you must have it here otherwise it will keep all $_GET parameters empty in your php file.
Option MultiViews (see http://httpd.apache.org/docs/2.4/content-negotiation.html) is used by Apache's content negotiation module that runs before mod_rewrite and makes Apache server match extensions of files. So if /file is the URL then Apache will serve /file.html.
I am trying to create the following behavior with a rewrite rule.
https://domain.com/admin/user/add => /addedit.php?add=
https://domain.com/admin/user/add/ => /addedit.php?add=
https://domain.com/admin/user/add/123 => /addedit.php?add=123
https://domain.com/admin/user/add/123/ => /addedit.php?add=123
user is variable
add can either be "add" or "edit"
Trailing slashes are always allowed
There can be more after the slash after (add|edit) which is assigned to the variable
I'm fine up until the optional slash after the action word (add|edit). That's where I don't know regex well enough to accomplish my goal.
Something like the following works:
RewriteRule ^admin/(.*)/(add|edit)(/(.*)/?)?$ /admin/$1/addedit.php?$2=$3
However, the URLs end up containing the slashes in the GET variable. I figured I would be able to reference the (.*) in middle of (/(.*)/?)? as $4, but I am not.
I then read about non capturing groups and so added a ?: like so:
RewriteRule ^admin/(.*)/(add|edit)(?:/(.*)/?)?$ /admin/$1/addedit.php?$2=$3
It's probably a relatively simple thing I'm overlooking.
You're almost there, just minor modifications needed:
RewriteRule ^admin/([^/]+)/(add|edit)(?:/([^/]*))?/?$ /admin/$1/addedit.php?$2=$3 [L,NC]
Regex to match: ^(.*\/admin)(\/user)\/((?:add)|(?:edit))\/?(([^/]*)?\/?)$
Regex to replace: /addedit.php?$3=$5
http://regexr.com?36gp3
I'm trying to write a rule that when user types in this url:
domain.com/09/13/2013/thisIsMyPageTitle
That url stays in browser window, but content from this url is displayed:
domain.com/contentlibrary/thisIsMyPageTitle
This is my rule that I currently get an error with:
RewriteEngine On
RewriteRule ^((0[1-9]|1[012])[- /.](0[1-9]|[12][0-9]|3[01])[- /.](19|20)\d\d[/])$(.*) /contentlibrary/$1 [L]
I'm trying to match the date with regular expression, and use the (.*) from the initial url in the second one that holds the content and actually exists.
If you're not going to do anything with date then why bother being precise with date semantics. You can simplify your regex:
RewriteRule ^[0-9]+/[0-9]+/[0-9]+/([^/]+)/?$ /contentlibrary/$1 [L]
The error that you're getting is probably because you have unescaped spaces in your regex. Specifically these:
[- /.]
The spaces get interpreted by mod_rewrite as the delimiter between parameters. Additionally, you have this:
$(.*)
at the end of your pattern. The $ matches the end of the string, so you want those swapped:
(.*)$
So:
^((0[1-9]|1[012])[-\ /.](0[1-9]|[12][0-9]|3[01])[-\ /.](19|20)\d\d[/])(.*)$
shold be the pattern that you want.
I need to rewrite URLs similar to
/b
to
/img/b.png
as well as URLs similar to
/b_c
to
/img/b_c.png
I have tried this:
RewriteRule ^b(?:/_c/)$ /img/$1.png
Which works for the first case but not the second (it is not matching "_c" and grouping it).
I need the literal string "_c" to be grouped and placed in the rewritten URL.
How can I accomplish this?
Try RewriteRule ^(b(_c)?)$ /img/$1.png.
This makes $1 the entire bracket backreference, and makes the _c optional, but it must be all there (you can't have b_ matching - though it can match if you want).
How would you create a regular expression that would parse the following url
http://example.com/answers/38-my-example-question-on-regular-expression
Specifically, "/answers/38-my-example-question-on-regular-expression" versus "/answers/category"
If the regex finds "38" a number, then it does this:
RewriteRule answers/([-_~*a-zA-Z0-9]+)(\/)?$ answers/view.php?title=$1&id=$2&%{QUERY_STRING}
else:
RewriteRule answers/([-_~*a-zA-Z0-9]+)(\/)?$ answers/categories.php?key=$1
I want to place the regex in the .httaccess for my webapp.
Thanks!
RewriteRule answers/([0-9]+)-?([-~a-zA-Z0-9/]*)/?$ answers/view.php?title=$2&id=$1&%{QUERY_STRING}
RewriteRule answers/([-~a-zA-Z0-9]+)/?$ answers/categories.php?key=$1
The two expressions - one looks for one or more numbers followed by a potential - and more characters to make up the title. The other looks for anything else and calls it a category.