Skip to content

Commit

Permalink
Merge pull request #558 from nextcloud-libraries/feat/noid/get-base-u…
Browse files Browse the repository at this point in the history
…rl-method

feat: add method to get a base URL, allow to pass remote base
  • Loading branch information
Antreesy authored Jan 29, 2024
2 parents 88ee39a + bec5dd4 commit 1a4ccc4
Show file tree
Hide file tree
Showing 3 changed files with 63 additions and 9 deletions.
32 changes: 29 additions & 3 deletions __tests__/urls.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -38,11 +38,27 @@ describe('URL generation', () => {
}
})

test('generateRemoteUrl', () => {
window._oc_webroot = '/nextcloud'
expect(generateRemoteUrl('dav')).toBe(`${window.location.href}nextcloud/remote.php/dav`)
describe('generateRemoteUrl', () => {
beforeEach(() => {
window._oc_webroot = ''
})

it('uses base URL by default', () => {
expect(generateRemoteUrl('dav')).toBe(`${window.location.origin}/remote.php/dav`)
})

it('replaces base URL with given one', () => {
const baseURL = 'https://remote-url.com'
expect(generateRemoteUrl('dav', { baseURL })).toBe(`${baseURL}/remote.php/dav`)
})

it('includes webroot', () => {
window._oc_webroot = '/nextcloud'
expect(generateRemoteUrl('dav')).toBe(`${window.location.origin}/nextcloud/remote.php/dav`)
})
})


describe('generateOcsUrl', () => {
beforeEach(() => {
window._oc_webroot = ''
Expand All @@ -56,6 +72,11 @@ describe('URL generation', () => {
expect(generateOcsUrl('/foo/bar', undefined, { ocsVersion: 1 })).toBe(`${window.location.href}ocs/v1.php/foo/bar`)
})

it('replaces base URL with given one', () => {
const baseURL = 'https://remote-url.com'
expect(generateOcsUrl('/foo/bar', undefined, { baseURL })).toBe(`${baseURL}/ocs/v2.php/foo/bar`)
})

it('starts with webroot', () => {
window._oc_webroot = '/nextcloud'
expect(generateOcsUrl('/foo/bar')).toBe(`${window.location.href}nextcloud/ocs/v2.php/foo/bar`)
Expand Down Expand Up @@ -83,6 +104,11 @@ describe('URL generation', () => {
expect(generateUrl('foo')).toBe('/foo')
})

it('replaces base URL with given one', () => {
const baseURL = 'https://remote-url.com'
expect(generateUrl('/foo/bar', undefined, { baseURL })).toBe(`${baseURL}/index.php/foo/bar`)
})

it('respects disabled mod-rewrite', () => {
expect(generateUrl('/foo/bar')).toMatch(/index\.php/)
})
Expand Down
7 changes: 6 additions & 1 deletion __tests__/webroot.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
*/

import { describe, expect, test } from 'vitest'
import { getAppRootUrl, getRootUrl } from '../lib/index'
import { getAppRootUrl, getBaseUrl, getRootUrl } from '../lib/index'

declare global {
interface Window {
Expand All @@ -34,30 +34,35 @@ describe('Web root handling', () => {
test('empty web root', () => {
window._oc_webroot = ''
expect(getRootUrl()).toBe('')
expect(getBaseUrl()).toBe(window.location.origin)
})

test('with given web root', () => {
window._oc_webroot = '/nextcloud'
expect(getRootUrl()).toBe('/nextcloud')
expect(getBaseUrl()).toBe(`${window.location.origin}/nextcloud`)
})

test('without web root configured', () => {
window._oc_webroot = undefined
window.location.pathname = '/index.php/apps/files'
expect(getRootUrl()).toBe('')
expect(getBaseUrl()).toBe(window.location.origin)
})

test('with implicit web root', () => {
window._oc_webroot = undefined
window.location.pathname = '/nextcloud/index.php/apps/files'
expect(getRootUrl()).toBe('/nextcloud')
expect(getBaseUrl()).toBe(`${window.location.origin}/nextcloud`)
})

// TODO: This seems to be wrong, would expect `/nextcloud`
test('with implicit web root and path rename', () => {
window._oc_webroot = undefined
window.location.pathname = '/nextcloud/apps/files'
expect(getRootUrl()).toBe('/nextcloud/apps')
expect(getBaseUrl()).toBe(`${window.location.origin}/nextcloud/apps`)
})
})

Expand Down
33 changes: 28 additions & 5 deletions lib/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,12 @@ export interface UrlOptions {
* @default 2
*/
ocsVersion?: number

/**
* URL to use as a base (defaults to current instance)
* @default ''
*/
baseURL?: string
}

/**
Expand All @@ -36,14 +42,18 @@ export const linkTo = (app: string, file: string) => generateFilePath(app, '', f
* @param {string} service id
* @return {string} the url
*/
const linkToRemoteBase = (service: string) => getRootUrl() + '/remote.php/' + service
const linkToRemoteBase = (service: string) => '/remote.php/' + service

/**
* Creates an absolute url for remote use
* @param {string} service id
* @return {string} the url
* @param {UrlOptions} [options] options for the parameter replacement
*/
export const generateRemoteUrl = (service: string) => window.location.protocol + '//' + window.location.host + linkToRemoteBase(service)
export const generateRemoteUrl = (service: string, options?: UrlOptions) => {
const baseURL = options?.baseURL ?? getBaseUrl()
return baseURL + linkToRemoteBase(service)
}

/**
* Get the base path for the given OCS API service
Expand All @@ -59,8 +69,9 @@ export const generateOcsUrl = (url: string, params?: object, options?: UrlOption
}, options || {})

const version = (allOptions.ocsVersion === 1) ? 1 : 2
const baseURL = options?.baseURL ?? getBaseUrl()

return window.location.protocol + '//' + window.location.host + getRootUrl() + '/ocs/v' + version + '.php' + _generateUrlPath(url, params, options)
return baseURL + '/ocs/v' + version + '.php' + _generateUrlPath(url, params, options)
}

/**
Expand Down Expand Up @@ -101,6 +112,7 @@ const _generateUrlPath = (url: string, params?: object, options?: UrlOptions) =>

/**
* Generate the url with webroot for the given relative url, which can contain parameters
* If options.baseURL is provided, generate the absolute url pointing ro remote server
*
* Parameters will be URL encoded automatically
*
Expand All @@ -114,11 +126,13 @@ export const generateUrl = (url: string, params?: object, options?: UrlOptions)
noRewrite: false,
}, options || {})

const baseOrRootURL = options?.baseURL ?? getRootUrl()

if (window?.OC?.config?.modRewriteWorking === true && !allOptions.noRewrite) {
return getRootUrl() + _generateUrlPath(url, params, options)
return baseOrRootURL + _generateUrlPath(url, params, options)
}

return getRootUrl() + '/index.php' + _generateUrlPath(url, params, options)
return baseOrRootURL + '/index.php' + _generateUrlPath(url, params, options)
}

/**
Expand Down Expand Up @@ -189,6 +203,15 @@ export const generateFilePath = (app: string, type: string, file: string) => {
return link
}

/**
* Return the full base URL where this Nextcloud instance
* is accessible, with a web root included.
* For example "https://company.com/nextcloud".
*
* @return {string} base URL
*/
export const getBaseUrl = () => window.location.protocol + '//' + window.location.host + getRootUrl()

/**
* Return the web root path where this Nextcloud instance
* is accessible, with a leading slash.
Expand Down

0 comments on commit 1a4ccc4

Please sign in to comment.