【问题标题】:Check whether a string is a valid URL in Delphi?在Delphi中检查字符串是否是有效的URL?
【发布时间】:2021-10-10 10:02:36
【问题描述】:

在 Windows 10 中的 Delphi 10.4.2 win-32 VCL 应用程序中,我尝试检查字符串是否为有效 URL。

当然,我已经检查了答案:https://stackoverflow.com/search?q=delphi+check+valid+url
和:What is the best regular expression to check if a string is a valid URL?

其中一些正则表达式太长(例如 5500 个字符),以至于它们不能作为字符串常量粘贴到 Delphi 代码编辑器中。其他人根本无法在这种情况下工作(Delphi)。

这是我尝试过的,使用TRegExShLwApi

function TformMain.IsValidURL(const AUrl: string): Boolean;
const
  RE = '/((([A-Za-z]{3,9}:(?:\/\/)?)(?:[-;:&=\+\$,\w]+@)?[A-Za-z0-9.-]+(:[0-9]+)?|(?:www.|[-;:&=\+\$,\w]+@)[A-Za-z0-9.-]+)((?:\/[\+~%\/.\w-_]*)?\??(?:[-\+=&;%@.\w_]*)#?(?:[\w]*))?)/';
begin
  Result := False;
  if AUrl = '' then EXIT;

  // Does not work: 'https://www.google.c' is detected as valid:
  //Result := TRegEx.IsMatch(AUrl, '\A\b(?:(?:https?|ftps?|file)://|www\.|ftp|com\.)[-A-Z0-9+&@#/%=~_|$?!:,.]*[A-Z0-9+&@#/%=~_|$]\z', [roIgnoreCase]);

  // Does not work: almost everything starting with 'https:' is valid:
  //Result := Boolean(ShLwApi.PathIsURL(PChar(AUrl)));

  // Does not work with 'https://www.google.com':
  //Result := TRegEx.IsMatch(AUrl, RE, [roIgnoreCase]);
end;

解决方案应仅基于字符串(不连接到 Internet)。

我怀疑可能必须有一个非常简单的解决方案。

【问题讨论】:

  • "它们不能在 Delphi 代码编辑器中粘贴为字符串常量" - 您可以将多个文字连接成一个常量,然后轻松保存 5500 个字符。它不必是一个很长的文字/行:const RE= 'one'+ 'two'+ 'three'...;
  • 正则表达式中的 [\+~%\/.\w-_] 可能被视为无效范围 - 它甚至编译了吗?将 - 更改为 \- 以确保正则表达式引擎理解您想要的内容。
  • 这可能不适用于您的方案,但为了其他可能会看到此 StackOverflow 问题的人的利益:请注意,URL 可能与教科书示例 http://www.example.com 看起来有些不同。例如,TL​​D 的集合正在增加:example.beerexample.theatreexample.sydneymany others。此列表将来可能会扩展,因此硬编码允许的 TLD 列表是不明智的。此外,URL 可能没有 TLD:rejbrandcloud127.0.0.1:80
  • 这也是一个有效的 URL:http://admin:1grg34bAA@hörsës/things(1,2)?a=5#µ

标签: regex delphi url delphi-10.4-sydney


【解决方案1】:

Delphi 10.4.2 在System.Net.URLClient.pas 中提供了一条记录TURI。使用您的 URL 调用构造函数 Create 将针对无效 URL 引发 ENetURIException

【讨论】:

  • https://duck 没有引发这一事实非常好,因为这肯定是一个有效的 URL。例如,如果我将我的个人云重命名为 duck,那么我会在 Firefox 中输入 https://duck 来访问它。
  • 我在这里陷入了两难境地:验证应该检查 URL 是否与 Winapi.WinInet.InternetOpen 一起工作,而无需连接到 Internet。这在逻辑上是不可能的,不是吗?
  • 我已经意识到这种 URL STRING 验证是不可能的,例如一个检查字符串是否礼貌的函数:function StringIsPolite(const S: string);
  • @user1580348:这听起来是一个非常明智的结论。 (一个教科书示例:不要编写一个函数来检查您是否对特定目录具有写入权限。相反,尝试写入它并处理可能发生的任何故障。)
  • 我想说的是:Internet 是一个完全超出编程语言领域的参考系统(又名universe):如果不进入,你就无法对另一个宇宙中的事物发表声明它并成为它的一部分。
猜你喜欢
  • 2010-12-23
  • 2011-11-26
  • 2013-02-13
  • 1970-01-01
  • 2015-03-05
  • 1970-01-01
  • 1970-01-01
  • 2019-05-05
  • 2019-10-04
相关资源
最近更新 更多