feat: ability to generate url shorten config
This commit is contained in:
parent
81e6e4e5f2
commit
6d49463dad
5 changed files with 92 additions and 25 deletions
|
@ -7,28 +7,31 @@ export default function Flameshot({ user, open, setOpen }) {
|
||||||
const curl = [
|
const curl = [
|
||||||
'curl',
|
'curl',
|
||||||
'-H',
|
'-H',
|
||||||
'"Content-Type: multipart/form-data"',
|
|
||||||
'-H',
|
|
||||||
`"authorization: ${user?.token}"`,
|
`"authorization: ${user?.token}"`,
|
||||||
'-F',
|
|
||||||
'file=@/tmp/ss.png',
|
|
||||||
`${
|
`${
|
||||||
window.location.protocol +
|
window.location.protocol +
|
||||||
'//' +
|
'//' +
|
||||||
window.location.hostname +
|
window.location.hostname +
|
||||||
(window.location.port ? ':' + window.location.port : '')
|
(window.location.port ? ':' + window.location.port : '')
|
||||||
}/api/upload`,
|
}/api/${values.type === 'upload-file' ? 'upload' : 'shorten'}`,
|
||||||
];
|
];
|
||||||
|
|
||||||
|
if (values.type === 'upload-file') {
|
||||||
|
curl.push('-F', 'file=@/tmp/ss.png');
|
||||||
|
curl.push('-H', '"Content-Type: multipart/form-data"');
|
||||||
|
} else {
|
||||||
|
curl.push('-H', '"Content-Type: application/json"');
|
||||||
|
}
|
||||||
|
|
||||||
const extraHeaders = {};
|
const extraHeaders = {};
|
||||||
|
|
||||||
if (values.format !== 'RANDOM') {
|
if (values.format !== 'RANDOM' && values.type === 'upload-file') {
|
||||||
extraHeaders['Format'] = values.format;
|
extraHeaders['Format'] = values.format;
|
||||||
} else {
|
} else {
|
||||||
delete extraHeaders['Format'];
|
delete extraHeaders['Format'];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (values.imageCompression !== 0) {
|
if (values.imageCompression !== 0 && values.type === 'upload-file') {
|
||||||
extraHeaders['Image-Compression-Percent'] = values.imageCompression;
|
extraHeaders['Image-Compression-Percent'] = values.imageCompression;
|
||||||
} else {
|
} else {
|
||||||
delete extraHeaders['Image-Compression-Percent'];
|
delete extraHeaders['Image-Compression-Percent'];
|
||||||
|
@ -40,16 +43,16 @@ export default function Flameshot({ user, open, setOpen }) {
|
||||||
delete extraHeaders['Zws'];
|
delete extraHeaders['Zws'];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (values.embed) {
|
if (values.embed && values.type === 'upload-file') {
|
||||||
extraHeaders['Embed'] = 'true';
|
extraHeaders['Embed'] = 'true';
|
||||||
} else {
|
} else {
|
||||||
delete extraHeaders['Embed'];
|
delete extraHeaders['Embed'];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (values.noJSON) {
|
if (values.noJSON) {
|
||||||
extraHeaders['X-Zipline-NoJSON'] = 'true';
|
extraHeaders['No-JSON'] = 'true';
|
||||||
} else {
|
} else {
|
||||||
delete extraHeaders['X-Zipline-NoJSON'];
|
delete extraHeaders['No-JSON'];
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const [key, value] of Object.entries(extraHeaders)) {
|
for (const [key, value] of Object.entries(extraHeaders)) {
|
||||||
|
@ -57,16 +60,28 @@ export default function Flameshot({ user, open, setOpen }) {
|
||||||
curl.push(`"${key}: ${value}"`);
|
curl.push(`"${key}: ${value}"`);
|
||||||
}
|
}
|
||||||
|
|
||||||
const shell = `#!/bin/bash${values.wlCompositorNotSupported ? '\nexport XDG_CURRENT_DESKTOP=sway\n' : ''}
|
console.log(curl);
|
||||||
|
|
||||||
|
let shell;
|
||||||
|
if (values.type === 'upload-file') {
|
||||||
|
shell = `#!/bin/bash${values.wlCompositorNotSupported ? '\nexport XDG_CURRENT_DESKTOP=sway\n' : ''}
|
||||||
flameshot gui -r > /tmp/ss.png;
|
flameshot gui -r > /tmp/ss.png;
|
||||||
${curl.join(' ')}${values.noJSON ? '' : " | jq -r '.files[0]'"} | tr -d '\\n' | ${
|
${curl.join(' ')}${values.noJSON ? '' : " | jq -r '.files[0]'"} | tr -d '\\n' | ${
|
||||||
values.wlCompatibility ? 'wl-copy' : 'xsel -ib'
|
values.wlCompatibility ? 'wl-copy' : 'xsel -ib'
|
||||||
};
|
};
|
||||||
`;
|
`;
|
||||||
|
} else if (values.type === 'shorten-url') {
|
||||||
|
shell = `#!/bin/bash
|
||||||
|
arg=$1;
|
||||||
|
${curl.join(' ')} -d "{\\"url\\": \\"$arg\\"}"${values.noJSON ? '' : " | jq -r '.url'"} | tr -d '\\n' | ${
|
||||||
|
values.wlCompatibility ? 'wl-copy' : 'xsel -ib'
|
||||||
|
};
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
const pseudoElement = document.createElement('a');
|
const pseudoElement = document.createElement('a');
|
||||||
pseudoElement.setAttribute('href', 'data:text/plain;charset=utf-8,' + encodeURIComponent(shell));
|
pseudoElement.setAttribute('href', 'data:text/plain;charset=utf-8,' + encodeURIComponent(shell));
|
||||||
pseudoElement.setAttribute('download', 'zipline.sh');
|
pseudoElement.setAttribute('download', `zipline${values.type === 'upload-file' ? '' : '-url'}.sh`);
|
||||||
pseudoElement.style.display = 'none';
|
pseudoElement.style.display = 'none';
|
||||||
document.body.appendChild(pseudoElement);
|
document.body.appendChild(pseudoElement);
|
||||||
pseudoElement.click();
|
pseudoElement.click();
|
||||||
|
|
|
@ -3,10 +3,12 @@ import { useForm } from '@mantine/form';
|
||||||
import { DownloadIcon } from 'components/icons';
|
import { DownloadIcon } from 'components/icons';
|
||||||
import Link from 'components/Link';
|
import Link from 'components/Link';
|
||||||
import MutedText from 'components/MutedText';
|
import MutedText from 'components/MutedText';
|
||||||
|
import { useState } from 'react';
|
||||||
|
|
||||||
export function GeneratorModal({ opened, onClose, title, onSubmit, ...other }) {
|
export function GeneratorModal({ opened, onClose, title, onSubmit, ...other }) {
|
||||||
const form = useForm({
|
const form = useForm({
|
||||||
initialValues: {
|
initialValues: {
|
||||||
|
type: 'upload-file',
|
||||||
format: 'RANDOM',
|
format: 'RANDOM',
|
||||||
imageCompression: 0,
|
imageCompression: 0,
|
||||||
zeroWidthSpace: false,
|
zeroWidthSpace: false,
|
||||||
|
@ -17,6 +19,13 @@ export function GeneratorModal({ opened, onClose, title, onSubmit, ...other }) {
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const [isUploadFile, setIsUploadFile] = useState(true);
|
||||||
|
|
||||||
|
const onChangeType = (value) => {
|
||||||
|
setIsUploadFile(value === 'upload-file');
|
||||||
|
form.setFieldValue('type', value);
|
||||||
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal opened={opened} onClose={onClose} title={<Title order={3}>{title}</Title>} size='lg'>
|
<Modal opened={opened} onClose={onClose} title={<Title order={3}>{title}</Title>} size='lg'>
|
||||||
{other.desc && (
|
{other.desc && (
|
||||||
|
@ -25,6 +34,18 @@ export function GeneratorModal({ opened, onClose, title, onSubmit, ...other }) {
|
||||||
</MutedText>
|
</MutedText>
|
||||||
)}
|
)}
|
||||||
<form onSubmit={form.onSubmit((values) => onSubmit(values))}>
|
<form onSubmit={form.onSubmit((values) => onSubmit(values))}>
|
||||||
|
<Select
|
||||||
|
label='Type'
|
||||||
|
data={[
|
||||||
|
{ value: 'upload-file', label: 'Upload file' },
|
||||||
|
{ value: 'shorten-url', label: 'Shorten URLs' },
|
||||||
|
]}
|
||||||
|
id='type'
|
||||||
|
my='sm'
|
||||||
|
{...form.getInputProps('type')}
|
||||||
|
onChange={onChangeType}
|
||||||
|
/>
|
||||||
|
|
||||||
<Select
|
<Select
|
||||||
label='Select file name format'
|
label='Select file name format'
|
||||||
data={[
|
data={[
|
||||||
|
@ -34,6 +55,8 @@ export function GeneratorModal({ opened, onClose, title, onSubmit, ...other }) {
|
||||||
{ value: 'NAME', label: 'Name (keeps original file name)' },
|
{ value: 'NAME', label: 'Name (keeps original file name)' },
|
||||||
]}
|
]}
|
||||||
id='format'
|
id='format'
|
||||||
|
my='sm'
|
||||||
|
disabled={!isUploadFile}
|
||||||
{...form.getInputProps('format')}
|
{...form.getInputProps('format')}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
@ -42,8 +65,9 @@ export function GeneratorModal({ opened, onClose, title, onSubmit, ...other }) {
|
||||||
description='Set the image compression level (0-100). 0 is no compression, 100 is maximum compression.'
|
description='Set the image compression level (0-100). 0 is no compression, 100 is maximum compression.'
|
||||||
max={100}
|
max={100}
|
||||||
min={0}
|
min={0}
|
||||||
mt='md'
|
my='sm'
|
||||||
id='imageCompression'
|
id='imageCompression'
|
||||||
|
disabled={!isUploadFile}
|
||||||
{...form.getInputProps('imageCompression')}
|
{...form.getInputProps('imageCompression')}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
@ -58,6 +82,7 @@ export function GeneratorModal({ opened, onClose, title, onSubmit, ...other }) {
|
||||||
description='Image will display with embedded metadata'
|
description='Image will display with embedded metadata'
|
||||||
label='Embed'
|
label='Embed'
|
||||||
id='embed'
|
id='embed'
|
||||||
|
disabled={!isUploadFile}
|
||||||
{...form.getInputProps('embed', { type: 'checkbox' })}
|
{...form.getInputProps('embed', { type: 'checkbox' })}
|
||||||
/>
|
/>
|
||||||
<Checkbox
|
<Checkbox
|
||||||
|
@ -106,6 +131,7 @@ export function GeneratorModal({ opened, onClose, title, onSubmit, ...other }) {
|
||||||
<Code>XDG_CURRENT_DESKTOP=sway</Code> to workaround Flameshot's errors
|
<Code>XDG_CURRENT_DESKTOP=sway</Code> to workaround Flameshot's errors
|
||||||
</>
|
</>
|
||||||
}
|
}
|
||||||
|
disabled={!isUploadFile}
|
||||||
id='wlCompositorNotSupported'
|
id='wlCompositorNotSupported'
|
||||||
{...form.getInputProps('wlCompositorNotSupported', { type: 'checkbox' })}
|
{...form.getInputProps('wlCompositorNotSupported', { type: 'checkbox' })}
|
||||||
/>
|
/>
|
||||||
|
|
|
@ -3,7 +3,7 @@ import { GeneratorModal } from './GeneratorModal';
|
||||||
|
|
||||||
export default function ShareX({ user, open, setOpen }) {
|
export default function ShareX({ user, open, setOpen }) {
|
||||||
const [config, setConfig] = useState({
|
const [config, setConfig] = useState({
|
||||||
Version: '13.2.1',
|
Version: '14.1.0',
|
||||||
Name: 'Zipline',
|
Name: 'Zipline',
|
||||||
DestinationType: 'ImageUploader, TextUploader',
|
DestinationType: 'ImageUploader, TextUploader',
|
||||||
RequestMethod: 'POST',
|
RequestMethod: 'POST',
|
||||||
|
@ -19,10 +19,28 @@ export default function ShareX({ user, open, setOpen }) {
|
||||||
URL: '$json:files[0]$',
|
URL: '$json:files[0]$',
|
||||||
Body: 'MultipartFormData',
|
Body: 'MultipartFormData',
|
||||||
FileFormName: 'file',
|
FileFormName: 'file',
|
||||||
|
Data: undefined,
|
||||||
});
|
});
|
||||||
|
|
||||||
const onSubmit = (values) => {
|
const onSubmit = (values) => {
|
||||||
if (values.format !== 'RANDOM') {
|
if (values.type === 'shorten-url') {
|
||||||
|
config.RequestURL = `${
|
||||||
|
window.location.protocol +
|
||||||
|
'//' +
|
||||||
|
window.location.hostname +
|
||||||
|
(window.location.port ? ':' + window.location.port : '')
|
||||||
|
}/api/shorten`;
|
||||||
|
config.URL = '$json:url$';
|
||||||
|
config.Body = 'JSON';
|
||||||
|
delete config.FileFormName;
|
||||||
|
config.Data = JSON.stringify({ url: '{input}' });
|
||||||
|
setConfig(config);
|
||||||
|
} else {
|
||||||
|
delete config.Data;
|
||||||
|
setConfig(config);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (values.format !== 'RANDOM' && values.type === 'upload-file') {
|
||||||
config.Headers['Format'] = values.format;
|
config.Headers['Format'] = values.format;
|
||||||
setConfig(config);
|
setConfig(config);
|
||||||
} else {
|
} else {
|
||||||
|
@ -30,7 +48,7 @@ export default function ShareX({ user, open, setOpen }) {
|
||||||
setConfig(config);
|
setConfig(config);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (values.imageCompression !== 0) {
|
if (values.imageCompression !== 0 && values.type === 'upload-file') {
|
||||||
config.Headers['Image-Compression-Percent'] = values.imageCompression;
|
config.Headers['Image-Compression-Percent'] = values.imageCompression;
|
||||||
setConfig(config);
|
setConfig(config);
|
||||||
} else {
|
} else {
|
||||||
|
@ -46,7 +64,7 @@ export default function ShareX({ user, open, setOpen }) {
|
||||||
setConfig(config);
|
setConfig(config);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (values.embed) {
|
if (values.embed && values.type === 'upload-file') {
|
||||||
config.Headers['Embed'] = 'true';
|
config.Headers['Embed'] = 'true';
|
||||||
setConfig(config);
|
setConfig(config);
|
||||||
} else {
|
} else {
|
||||||
|
@ -56,10 +74,11 @@ export default function ShareX({ user, open, setOpen }) {
|
||||||
|
|
||||||
if (values.noJSON) {
|
if (values.noJSON) {
|
||||||
config.URL = '{response}';
|
config.URL = '{response}';
|
||||||
config.Headers['X-Zipline-NoJSON'] = 'true';
|
config.Headers['No-JSON'] = 'true';
|
||||||
setConfig(config);
|
setConfig(config);
|
||||||
} else {
|
} else {
|
||||||
delete config.Headers['X-Zipline-NoJSON'];
|
delete config.Headers['No-JSON'];
|
||||||
|
config.URL = values.type === 'upload-file' ? '$json:files[0]$' : '$json:url$';
|
||||||
setConfig(config);
|
setConfig(config);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -66,10 +66,17 @@ async function handler(req: NextApiReq, res: NextApiRes) {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const fullUrl = `${zconfig.core.return_https ? 'https' : 'http'}://${req.headers.host}${
|
||||||
|
zconfig.uploader.route === '/' ? '' : zconfig.uploader.route
|
||||||
|
}/${req.body.vanity ? req.body.vanity : invis ? invis.invis : url.id}`;
|
||||||
|
|
||||||
|
if (req.headers['no-json']) {
|
||||||
|
res.setHeader('Content-Type', 'text/plain');
|
||||||
|
return res.end(fullUrl);
|
||||||
|
}
|
||||||
|
|
||||||
return res.json({
|
return res.json({
|
||||||
url: `${zconfig.core.return_https ? 'https' : 'http'}://${req.headers.host}${zconfig.urls.route}/${
|
url: fullUrl,
|
||||||
req.body.vanity ? req.body.vanity : invis ? invis.invis : url.id
|
|
||||||
}`,
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -374,7 +374,7 @@ async function handler(req: NextApiReq, res: NextApiRes) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (req.headers['x-zipline-nojson']) {
|
if (req.headers['no-json']) {
|
||||||
res.setHeader('Content-Type', 'text/plain');
|
res.setHeader('Content-Type', 'text/plain');
|
||||||
return res.end(response.files.join(','));
|
return res.end(response.files.join(','));
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue