From 28e8dc8e80995d4a3cb2048ee5775c553fcd4118 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jonas=20Sundstr=C3=B6m?= Date: Mon, 11 May 2009 00:48:03 +0000 Subject: [PATCH] Move Url class out of /bin/urlwrapper into BPrivate::Support. I plan to add a Launch()-method that will make it useful to /bin/open, AboutSystem, People and other applications. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@30702 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- headers/private/support/Url.h | 49 +++++++++ src/bin/Jamfile | 2 +- src/bin/urlwrapper.cpp | 105 +------------------ src/kits/support/Jamfile | 3 +- src/kits/support/Url.cpp | 189 ++++++++++++++++++++++++++++++++++ 5 files changed, 245 insertions(+), 103 deletions(-) create mode 100644 headers/private/support/Url.h create mode 100644 src/kits/support/Url.cpp diff --git a/headers/private/support/Url.h b/headers/private/support/Url.h new file mode 100644 index 0000000000..679cd7da91 --- /dev/null +++ b/headers/private/support/Url.h @@ -0,0 +1,49 @@ +/* + * Copyright 2007-2009, Haiku Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + */ +#ifndef _URL_H +#define _URL_H + +#include + +namespace BPrivate { +namespace Support { + +class BUrl : public BString { +public: + BUrl(const char *url); + ~BUrl(); + + status_t ParseAndSplit(); + status_t InitCheck() const; + + bool HasHost() const; + bool HasPort() const; + bool HasUser() const; + bool HasPass() const; + bool HasPath() const; + + BString Proto() const; + BString Full() const; + BString Host() const; + BString Port() const; + BString User() const; + BString Pass() const; + + BString proto; + BString full; + BString host; + BString port; + BString user; + BString pass; + BString path; +private: + status_t fStatus; +}; + +}; // namespace Support +}; // namespace BPrivate + +#endif // _URL_H + diff --git a/src/bin/Jamfile b/src/bin/Jamfile index 667c098fc0..24c54a2fa9 100644 --- a/src/bin/Jamfile +++ b/src/bin/Jamfile @@ -2,7 +2,7 @@ SubDir HAIKU_TOP src bin ; SetSubDirSupportedPlatformsBeOSCompatible ; -UsePrivateHeaders app shared storage usb ; +UsePrivateHeaders app shared storage support usb ; UsePrivateSystemHeaders ; SubDirHdrs $(HAIKU_TOP) src add-ons kernel file_cache ; diff --git a/src/bin/urlwrapper.cpp b/src/bin/urlwrapper.cpp index a076db235c..0afc9ef75e 100644 --- a/src/bin/urlwrapper.cpp +++ b/src/bin/urlwrapper.cpp @@ -21,6 +21,7 @@ #include #include #include +#include #include #include @@ -50,36 +51,6 @@ const char *kIMSig = "application/x-vnd.m_eiman.sample_im_client"; const char *kVLCSig = "application/x-vnd.videolan-vlc"; #endif -// TODO: make a public BUrl class for use by apps ? -class Url : public BString { -public: - Url(const char *url) : BString(url) { fStatus = ParseAndSplit(); }; - ~Url() {}; -status_t InitCheck() const { return fStatus; }; -status_t ParseAndSplit(); - -bool HasHost() const { return host.Length(); }; -bool HasPort() const { return port.Length(); }; -bool HasUser() const { return user.Length(); }; -bool HasPass() const { return pass.Length(); }; -bool HasPath() const { return path.Length(); }; -BString Proto() const { return BString(proto); }; -BString Full() const { return BString(full); }; // RFC1738's "sheme-part" -BString Host() const { return BString(host); }; -BString Port() const { return BString(port); }; -BString User() const { return BString(user); }; -BString Pass() const { return BString(pass); }; - -BString proto; -BString full; -BString host; -BString port; -BString user; -BString pass; -BString path; -private: -status_t fStatus; -}; class UrlWrapperApp : public BApplication { @@ -96,79 +67,10 @@ private: }; -// proto:[//]user:pass@host:port/path -status_t Url::ParseAndSplit() -{ - int32 v; - BString left; - - v = FindFirst(":"); - if (v < 0) - return B_BAD_VALUE; - - // TODO: proto and host should be lowercased. - // see http://en.wikipedia.org/wiki/URL_normalization - - CopyInto(proto, 0, v); - CopyInto(left, v + 1, Length() - v); - // TODO: RFC1738 says the // part should indicate the uri follows the u:p@h:p/path convention, so it should be used to check for special cases. - if (left.FindFirst("//") == 0) - left.RemoveFirst("//"); - full = left; - - // path part - // actually some apps handle file://[host]/path - // but I have no idea what proto it implies... - // or maybe it's just to emphasize on "localhost". - v = left.FindFirst("/"); - if (v == 0 || proto == "file") { - path = left; - return 0; - } - // some protos actually implies path if it's the only component - if ((v < 0) && (proto == "beshare" || proto == "irc")) { - path = left; - return 0; - } - - if (v > -1) { - left.MoveInto(path, v+1, left.Length()-v); - left.Remove(v, 1); - } - - // user:pass@host - v = left.FindFirst("@"); - if (v > -1) { - left.MoveInto(user, 0, v); - left.Remove(0, 1); - v = user.FindFirst(":"); - if (v > -1) { - user.MoveInto(pass, v, user.Length() - v); - pass.Remove(0, 1); - } - } else if (proto == "finger") { - // single component implies user - // see also: http://www.subir.com/lynx/lynx_help/lynx_url_support.html - user = left; - return 0; - } - - // host:port - v = left.FindFirst(":"); - if (v > -1) { - left.MoveInto(port, v + 1, left.Length() - v); - left.Remove(v, 1); - } - - // not much left... - host = left; - - return 0; -} status_t UrlWrapperApp::SplitUrl(const char *url, BString &host, BString &port, BString &user, BString &pass, BString &path) { - Url u(url); + BPrivate::Support::BUrl u(url); if (u.InitCheck() < 0) return u.InitCheck(); host = u.host; @@ -318,7 +220,7 @@ void UrlWrapperApp::ArgvReceived(int32 argc, char **argv) const char *pausec = " ; read -p 'Press any key'"; char *args[] = { "/bin/sh", "-c", NULL, NULL}; - Url u(argv[1]); + BPrivate::Support::BUrl u(argv[1]); BString url = u.Full(); if (u.InitCheck() < 0) { fprintf(stderr, "malformed url: '%s'\n", u.String()); @@ -578,3 +480,4 @@ int main(int argc, char **argv) app.Run(); return 0; } + diff --git a/src/kits/support/Jamfile b/src/kits/support/Jamfile index 31126dde36..04e85de9fa 100644 --- a/src/kits/support/Jamfile +++ b/src/kits/support/Jamfile @@ -2,7 +2,7 @@ SubDir HAIKU_TOP src kits support ; SetSubDirSupportedPlatforms haiku libbe_test ; -UsePrivateHeaders shared app media ; +UsePrivateHeaders shared app media support ; MergeObject support_kit.o : Archivable.cpp @@ -18,4 +18,5 @@ MergeObject support_kit.o : Referenceable.cpp StopWatch.cpp String.cpp + Url.cpp ; diff --git a/src/kits/support/Url.cpp b/src/kits/support/Url.cpp new file mode 100644 index 0000000000..39ed139cc5 --- /dev/null +++ b/src/kits/support/Url.cpp @@ -0,0 +1,189 @@ +/* + * Copyright 2007, Haiku. All rights reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * François Revol, revol@free.fr + * Jonas Sundström, jonas@kirilla.com + */ + +/*! Url class for parsing an URL and opening it with its preferred handler. */ + + +#include "Url.h" + +namespace BPrivate { +namespace Support { + +BUrl::BUrl(const char *url) + : BString(url) +{ + fStatus = ParseAndSplit(); +} + + +BUrl::~BUrl() +{ +} + + +status_t +BUrl::InitCheck() const +{ + return fStatus; +} + + +status_t +BUrl::ParseAndSplit() +{ + // proto:[//]user:pass@host:port/path + + int32 v; + BString left; + + v = FindFirst(":"); + if (v < 0) + return B_BAD_VALUE; + + // TODO: proto and host should be lowercased. + // see http://en.wikipedia.org/wiki/URL_normalization + + CopyInto(proto, 0, v); + CopyInto(left, v + 1, Length() - v); + // TODO: RFC1738 says the // part should indicate the uri follows the u:p@h:p/path convention, so it should be used to check for special cases. + if (left.FindFirst("//") == 0) + left.RemoveFirst("//"); + full = left; + + // path part + // actually some apps handle file://[host]/path + // but I have no idea what proto it implies... + // or maybe it's just to emphasize on "localhost". + v = left.FindFirst("/"); + if (v == 0 || proto == "file") { + path = left; + return 0; + } + // some protos actually implies path if it's the only component + if ((v < 0) && (proto == "beshare" || proto == "irc")) { + path = left; + return 0; + } + + if (v > -1) { + left.MoveInto(path, v+1, left.Length()-v); + left.Remove(v, 1); + } + + // user:pass@host + v = left.FindFirst("@"); + if (v > -1) { + left.MoveInto(user, 0, v); + left.Remove(0, 1); + v = user.FindFirst(":"); + if (v > -1) { + user.MoveInto(pass, v, user.Length() - v); + pass.Remove(0, 1); + } + } else if (proto == "finger") { + // single component implies user + // see also: http://www.subir.com/lynx/lynx_help/lynx_url_support.html + user = left; + return 0; + } + + // host:port + v = left.FindFirst(":"); + if (v > -1) { + left.MoveInto(port, v + 1, left.Length() - v); + left.Remove(v, 1); + } + + // not much left... + host = left; + + return 0; +} + + +bool +BUrl::HasHost() const +{ + return host.Length(); +} + + +bool +BUrl::HasPort() const +{ + return port.Length(); +} + + +bool +BUrl::HasUser() const +{ + return user.Length(); +} + + +bool +BUrl::HasPass() const +{ + return pass.Length(); +} + + +bool +BUrl::HasPath() const +{ + return path.Length(); +} + + +BString +BUrl::Proto() const +{ + return BString(proto); +} + + +BString +BUrl::Full() const +{ + // RFC1738's "sheme-part" + return BString(full); +} + + +BString +BUrl::Host() const +{ + return BString(host); +} + + +BString +BUrl::Port() const +{ + return BString(port); +} + + +BString +BUrl::User() const +{ + return BString(user); +} + + +BString +BUrl::Pass() const +{ + return BString(pass); +} + +}; // namespace Support +}; // namespace BPrivate +