1
0
mirror of https://github.com/chylex/Nextcloud-Desktop.git synced 2026-04-17 18:44:09 +02:00

Compare commits

...

3 Commits

Author SHA1 Message Date
Jocelyn Turcotte
23e248b5d1 shell_integration: Fetch the share menu title from the client on Windows
The context menu will now show "Share with ownCloud" instead of "Share" as
it does on other platforms.

This also updates the submodule to point to matching binaries.
2015-02-13 16:08:39 +01:00
Christian Kamm
40dbc78407 concatUrl: Remove manual parsing, add test. #2817 2015-02-13 14:53:55 +01:00
Klaas Freitag
b159018f51 Changelog edited for 1.8.0 2015-02-13 12:54:27 +01:00
11 changed files with 180 additions and 54 deletions

View File

@@ -1,5 +1,32 @@
ChangeLog
=========
version 1.8.0 (release 2015-02-xx)
* Mac OS: HIDPI support
* Support Sharing from desktop: Added a share dialog that can be
opened by context menu in the file managers (Win, Mac, Nautilus)
Supports public links with password enforcement
* Enhanced usage of parallel HTTP requests for ownCloud 8 servers
* Renamed github repository from mirall to client.
* Mac OS: Use native notification support
* Selective Sync: allow to enforce selective sync in brandings.
* Added ability to build on Windows utilizing MingGW
* SQLite database fixes if running on FAT filesystems
* Improved detection of changing files to upload from local
* Preparations for the muli-account feature
* Fixed experience for Window manager without system tray
* Build with Qt 5.4
* Dropped libneon dependency if Qt 5.4 is available
* Keep files open very short, that avoid lock problems on Windows
especially with office software but also others.
* Merged some NetBSD patches
* Selective sync support for owncloudcmd
* Reorganize the source repository
* Prepared direct download
* Added Crashreporter feature to be switched on on demand
* A huge amount of bug fixes in all areas of the client.
* more than 7000 commits since 1.7.0
version 1.7.1 (release 2014-12-18)
* Documentation fixes and updates
* Nautilus Python plugin fixed for Python 3

2
binary

Submodule binary updated: 96dd38811b...5a664de4d3

View File

@@ -81,7 +81,7 @@ file manager integration works.
.. image:: images/client8.png
When you are in your local ownCloud folder you can right-click any file or
folder, and then left-click Share to create a share link. Note that Windows
folder, and then left-click "Share with ownCloud" to create a share link. Note that Windows
may also have a Share With option. This is not the ownCloud Share option. The
ownCloud share dialog looks like the following example:

View File

@@ -34,28 +34,33 @@ using namespace std;
#define PIPE_TIMEOUT 5*1000 //ms
#define SOCK_BUFFER 4096
std::vector<std::wstring> OCClientInterface::WatchedDirectories()
OCClientInterface::ContextMenuInfo OCClientInterface::FetchInfo()
{
auto pipename = std::wstring(L"\\\\.\\pipe\\");
pipename += L"ownCloud";
CommunicationSocket socket;
if (!WaitNamedPipe(pipename.data(), PIPE_TIMEOUT)) {
return std::vector<std::wstring>();
return {};
}
if (!socket.Connect(pipename)) {
return std::vector<std::wstring>();
return {};
}
std::vector<std::wstring> watchedDirectories;
socket.SendMsg(L"SHARE_MENU_TITLE\n");
ContextMenuInfo info;
std::wstring response;
Sleep(50);
while (socket.ReadLine(&response)) {
if (StringUtil::begins_with(response, wstring(L"REGISTER_PATH:"))) {
wstring responsePath = response.substr(14); // length of REGISTER_PATH
watchedDirectories.push_back(responsePath);
info.watchedDirectories.push_back(responsePath);
}
else if (StringUtil::begins_with(response, wstring(L"SHARE_MENU_TITLE:"))) {
info.shareMenuTitle = response.substr(17); // length of SHARE_MENU_TITLE:
}
}
return watchedDirectories;
return info;
}
void OCClientInterface::ShareObject(const std::wstring &path)

View File

@@ -43,7 +43,11 @@ class CommunicationSocket;
class OCClientInterface
{
public:
static std::vector<std::wstring> WatchedDirectories();
struct ContextMenuInfo {
std::vector<std::wstring> watchedDirectories;
std::wstring shareMenuTitle;
};
static ContextMenuInfo FetchInfo();
static void ShareObject(const std::wstring &path);
};

View File

@@ -150,8 +150,9 @@ IFACEMETHODIMP OCContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu, UINT
return MAKE_HRESULT(SEVERITY_SUCCESS, 0, USHORT(0));
}
OCClientInterface::ContextMenuInfo info = OCClientInterface::FetchInfo();
bool skip = true;
for (const std::wstring path : OCClientInterface::WatchedDirectories()) {
for (const std::wstring path : info.watchedDirectories) {
if (StringUtil::begins_with(std::wstring(m_szSelectedFile), path)) {
skip = false;
break;
@@ -165,11 +166,12 @@ IFACEMETHODIMP OCContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu, UINT
InsertSeperator(hMenu, indexMenu);
indexMenu++;
assert(!info.shareMenuTitle.empty());
MENUITEMINFO mii = { sizeof(mii) };
mii.fMask = MIIM_BITMAP | MIIM_STRING | MIIM_FTYPE | MIIM_ID | MIIM_STATE;
mii.wID = idCmdFirst + IDM_SHARE;
mii.fType = MFT_STRING;
mii.dwTypeData = m_pszMenuText;
mii.dwTypeData = &info.shareMenuTitle[0];
mii.fState = MFS_ENABLED;
if (!InsertMenuItem(hMenu, indexMenu, TRUE, &mii))
{

View File

@@ -257,7 +257,10 @@ void ShareDialog::slotSharesFetched(const QString &reply)
if (versionString.contains('.') && versionString.split('.')[0].toInt() >= 8) {
url = Account::concatUrlPath(_account->url(), QString("index.php/s/%1").arg(data.value("token").toString())).toString();
} else {
url = Account::concatUrlPath(_account->url(), QString("public.php?service=files&t=%1").arg(data.value("token").toString())).toString();
QList<QPair<QString, QString>> queryArgs;
queryArgs.append(qMakePair(QString("service"), QString("files")));
queryArgs.append(qMakePair(QString("t"), data.value("token").toString()));
url = Account::concatUrlPath(_account->url(), QLatin1String("public.php"), queryArgs).toString();
}
_ui->lineEdit_shareLink->setText(url);
}

View File

@@ -380,10 +380,11 @@ void Account::setUrl(const QUrl &url)
_url = url;
}
QUrl Account::concatUrlPath(const QUrl &url, const QString &concatPath)
QUrl Account::concatUrlPath(const QUrl &url, const QString &concatPath,
const QList< QPair<QString, QString> > &queryItems)
{
QUrl tmpUrl = url;
QString path = tmpUrl.path();
QString path = url.path();
if (! concatPath.isEmpty()) {
// avoid '//'
if (path.endsWith('/') && concatPath.startsWith('/')) {
path.chop(1);
@@ -391,32 +392,10 @@ QUrl Account::concatUrlPath(const QUrl &url, const QString &concatPath)
else if (!path.endsWith('/') && !concatPath.startsWith('/')) {
path += QLatin1Char('/');
}
path += concatPath; // put togehter the complete path
QList< QPair<QString, QString> > queryItems;
// Check if there are query items within the path and if so, add them properly to the url.
if( path.contains(QLatin1Char('?')) ) {
// get the position of the delimiter between path and query items.
// remember: myphpscript.php?queryItem1=foo&queryItem2=bar
int cutPos = path.indexOf(QLatin1Char('?'));
if( cutPos > -1 ) {
QString itemStr = path.right(path.length() - cutPos-1);
// remote the query item part from the path.
if( cutPos < path.length() ) {
path.truncate(cutPos);
path += concatPath; // put the complete path together
}
// parse the query items into the list of QPairs of Strings.
QStringList items = itemStr.split(QLatin1Char('&'));
Q_FOREACH( QString item, items ) {
QStringList pair = item.split(QLatin1Char('='));
if( pair.size() > 1 ) {
queryItems.append( QPair<QString, QString>(pair.at(0), pair.at(1)) );
}
}
}
}
QUrl tmpUrl = url;
tmpUrl.setPath(path);
if( queryItems.size() > 0 ) {
tmpUrl.setQueryItems(queryItems);

View File

@@ -136,7 +136,8 @@ public:
void setSslErrorHandler(AbstractSslErrorHandler *handler);
// static helper function
static QUrl concatUrlPath(const QUrl &url, const QString &concatPath);
static QUrl concatUrlPath(const QUrl &url, const QString &concatPath,
const QList< QPair<QString, QString> > &queryItems = QList< QPair<QString, QString> >());
/** Returns a new settings pre-set in a specific group. The Settings will be created
with the given parent. If no parents is specified, the caller must destroy the settings */

View File

@@ -30,6 +30,7 @@ owncloud_add_test(NetrcParser ../src/cmd/netrcparser.cpp)
owncloud_add_test(OwnSql "")
owncloud_add_test(SyncJournalDB "")
owncloud_add_test(SyncFileItem "")
owncloud_add_test(ConcatUrl "")

104
test/testconcaturl.h Normal file
View File

@@ -0,0 +1,104 @@
/*
* This software is in the public domain, furnished "as is", without technical
* support, and with no warranty, express or implied, as to its usefulness for
* any purpose.
*
*/
#ifndef MIRALL_TESTCONCATURL_H
#define MIRALL_TESTCONCATURL_H
#include <QtTest>
#include <QUrl>
#include <QString>
#include "account.h"
using namespace OCC;
typedef QList< QPair<QString,QString> > QueryItems;
static QueryItems make()
{
return QueryItems();
}
static QueryItems make(QString key, QString value)
{
QueryItems q;
q.append(qMakePair(key, value));
return q;
}
static QueryItems make(QString key1, QString value1,
QString key2, QString value2)
{
QueryItems q;
q.append(qMakePair(key1, value1));
q.append(qMakePair(key2, value2));
return q;
}
class TestConcatUrl: public QObject
{
Q_OBJECT
private slots:
void testFolder()
{
QFETCH(QString, base);
QFETCH(QString, concat);
QFETCH(QueryItems, query);
QFETCH(QString, expected);
QUrl baseUrl("http://example.com" + base);
QUrl resultUrl = Account::concatUrlPath(baseUrl, concat, query);
QString result = QString::fromUtf8(resultUrl.toEncoded());
QString expectedFull = "http://example.com" + expected;
QCOMPARE(result, expectedFull);
}
void testFolder_data()
{
QTest::addColumn<QString>("base");
QTest::addColumn<QString>("concat");
QTest::addColumn<QueryItems>("query");
QTest::addColumn<QString>("expected");
// Tests about slashes
QTest::newRow("noslash1") << "/baa" << "foo" << make() << "/baa/foo";
QTest::newRow("noslash2") << "" << "foo" << make() << "/foo";
QTest::newRow("noslash3") << "/foo" << "" << make() << "/foo";
QTest::newRow("noslash4") << "" << "" << make() << "";
QTest::newRow("oneslash1") << "/bar/" << "foo" << make() << "/bar/foo";
QTest::newRow("oneslash2") << "/" << "foo" << make() << "/foo";
QTest::newRow("oneslash3") << "/foo" << "/" << make() << "/foo/";
QTest::newRow("oneslash4") << "" << "/" << make() << "/";
QTest::newRow("twoslash1") << "/bar/" << "/foo" << make() << "/bar/foo";
QTest::newRow("twoslash2") << "/" << "/foo" << make() << "/foo";
QTest::newRow("twoslash3") << "/foo/" << "/" << make() << "/foo/";
QTest::newRow("twoslash4") << "/" << "/" << make() << "/";
// Tests about path encoding
QTest::newRow("encodepath")
<< "/a f/b"
<< "/a f/c"
<< make()
<< "/a%20f/b/a%20f/c";
// Tests about query args
QTest::newRow("query1")
<< "/baa"
<< "/foo"
<< make("a=a", "b=b",
"c", "d")
<< "/baa/foo?a%3Da=b%3Db&c=d";
QTest::newRow("query2")
<< ""
<< ""
<< make("foo", "bar")
<< "?foo=bar";
}
};
#endif