2

I am using Discourse forum software. As in its current state, Discourse presents links to topic in two ways, with and without a post number at the end.

Example:

forum.domain.com/t/some-topic/23
forum.domain.com/t/some-topic/23/5

The first one is what I want and the second one I want to not be displayed in the forum at all.

I've written a post about it on Discourse forum but didn't receive an answer what Regex to put in the permalink normalization input field in the admin section.

I was told that there is an option to do it using permalink normalization like so (It's an example shown in the admin under the Regex input text, I didn't write it):

permalink normalizations

Apply the following regex before matching permalinks,
for example: /(topic.)\?./\1 will strip query strings from topic routes.
Format is regex+string use \1 etc. to access captures

I don't know what Regex I should use in order to remove the numerical value of the post number from links. I need it only for topic links.

This is the routes.rb routing library and this is the permalink.rb library (I think that the permalink library should help get a better clue how to achieve this). I have no idea how to approach this, because it seems that I need some knowledge of the Discourse routing to make it work. For example, I don't understand why (topic.) is part of the regex, what does it mean, so their example doesn't help me to find a solution.

In the admin I have an input field in which I nee to put the normalization regex code.

I need help with the Regex. I need the regex to work with all topics.

Things I've tried that didn't work out:

/(\/\d+)\/\d+$/\1

/(t/[^/]+/\d+).*/\1

/(\/\d+)\/[0-9]+$/\1

/(\/\d+)\/[0-9]+/\1

/(\/\d+)\/\d+$/\1/

/(forum.domain.com(\/\w+)*\/\d+)\/\d+(?=\s|$)/\1

Note: The Permalink Normalization input field treats the character | as a separator to separate between several Regex expressions.

Liron Harel
  • 10,819
  • 26
  • 118
  • 217
  • I don't know Discourse or its permalink management, but the regular expression for what you want could be `/(\/\d+)\/\d+$/\1`. A lot depends on what regular expression features are supported by Discourse. You might need to do without the `$` and/or replace each `\d` by `[0-9]`. – trincot Jul 09 '16 at 16:25
  • @trincot /t/ signifies a topic in discourse although I don't know what in the example they put (topic.), probably something related to the back routing coding in Discourse. – Liron Harel Jul 09 '16 at 16:38
  • Maybe `^/(t/some-topic/\d+).*/\1`? If the regex gets the string input as `/t/some-topic/23` when you have `forum.domain.com/t/some-topic/23`, this might work. You have been actually suggested `/(topic.*)\?.*/\1`, the asterisks have been lost due to poor formatting. – Wiktor Stribiżew Jul 09 '16 at 16:41
  • I don't think it is helpful to hard-code the "some-topic" in your regular expression, since you would want it to work for any topic. Also, I am quite sure "t" will be taken as a literal unless you prefix it with an escape character maybe. I looked for documentation by Discourse on this, but found none. Did you try what I suggested? – trincot Jul 09 '16 at 16:46
  • @WiktorStribiżew the /(topic.*)\?.*/\1 is not my suggestions, it's an example within Discourse. I will backup the server and try your regex. – Liron Harel Jul 09 '16 at 16:49
  • If you have a specific topic, hardcode it. If not, a section can be regexed as `[^/]+`. Say, to match `/t/this/45` and `/t/that/65` you may use `/t/[^/]+/\d+`. To use capture groups, place `(....)` around the part you need to keep, and reference that value with ``\``+digit that is the order of ap[pearance of the capturing group. So, you may try `/(t/[^/]+/\d+).*/\1` or `/^(/t/[^/]+/\d+).*/\1` (depending on what the `/.../` mean in the example). – Wiktor Stribiżew Jul 09 '16 at 16:51
  • I need it for all topics, I'll update the question – Liron Harel Jul 09 '16 at 16:51
  • @trincot I tried your suggestion /(\/\d+)\/\d+$/\1 and it didn't change anything (I excluded this suggestion in the question) – Liron Harel Jul 09 '16 at 17:00
  • Did you try the variations I proposed (removal of `$`, replace `\d`...)? – trincot Jul 09 '16 at 17:03
  • @trincot tried them both now without success – Liron Harel Jul 09 '16 at 17:06
  • @trincot I found the permalink library, maybe this can help: https://github.com/discourse/discourse/blob/master/app/models/permalink.rb – Liron Harel Jul 09 '16 at 17:14
  • I will have a look at that. At first glance I see that the expression needs to end with `/`, so could you try `/(\/\d+)\/\d+$/\1/` with a slash at the end? – trincot Jul 09 '16 at 17:20
  • @trincot still not working :( – Liron Harel Jul 09 '16 at 17:22
  • 1
    I suggest you mark your question with the `ruby on rails` tag, since discourse seems to written in that, and put this github link in your question as well. You need to attract ruby programmers to your question :) – trincot Jul 09 '16 at 17:27

3 Answers3

2

I think this may be the expression you are looking for to put inside de settings field:

/(t\/.*\/\d+)(\/\d+)/\1

You can see it working on Rubular.

However, the code that generates the url is not using the normalization code, so the expression is being ignored.

You could try normalizing the permalink there:

def last_post_url
  url = "#{Discourse.base_uri}/t/#{slug}/#{id}/#{posts_count}"
  url = Permalink.normalize_url url
  url
end
chipairon
  • 2,031
  • 2
  • 19
  • 21
0

I didn't truly understand your question, but if I got it right, you are saying that you want links with /some-number at the end but don't what links with /some-number/some-number at the end. If that is the case, the regex is:

forum\.domain\.com\/t\/[^0-9\/]+\/\d{1,9}$

You can replace 'forum' with your forum name and 'domain' with your domain name.

  • The links for topics should be only with one number at the end the signified the topic id, but not with the second number that signifies the post Id within the topic. I also need the Regex to be compatible with Discourse. They gave an example (which I showed in the question) and told me to follow the same rules. – Liron Harel Jul 09 '16 at 16:55
0

This will remove trailing "/<digits>" after another "/<digits>":

/(forum.domain.com(\/\w+)*\/\d+)\/\d+(?=\s|$)/\1
Bohemian
  • 412,405
  • 93
  • 575
  • 722
  • I tried that, Discourse still shows the links with the post Id at the end (as a second numerical value). Maybe the 'topic.' means something to the regex in Discourse, because I don't know why they use topic. in their example, maybe it's needed. – Liron Harel Jul 09 '16 at 17:03
  • It breaks the regex in the input field, probably a character that separate different regex expressions. The input field can accept several regex expressions and if I copy paste your regex, it breaks after the ?=\s, makes a regex out of the rest and leaves $)/\1 as a new text – Liron Harel Jul 09 '16 at 17:09
  • This is the permalink library: https://github.com/discourse/discourse/blob/master/app/models/permalink.rb – Liron Harel Jul 09 '16 at 17:14