From 7e2187285dd58591cd07aa948cf3001cffe3ff29 Mon Sep 17 00:00:00 2001 From: Dennis Eriksen Date: Mon, 3 Jul 2023 13:40:30 +0200 Subject: adding lincence, and some other useful stuff --- LICENCE | 26 ++++++++++++ README.md | 14 +++++++ nginx.conf | 35 ++++++++++++++++ sample.env | 16 ++++++++ schema.sql | 131 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ src/main.rs | 6 +-- 6 files changed, 225 insertions(+), 3 deletions(-) create mode 100644 LICENCE create mode 100644 README.md create mode 100644 nginx.conf create mode 100644 sample.env create mode 100644 schema.sql diff --git a/LICENCE b/LICENCE new file mode 100644 index 0000000..cb40b62 --- /dev/null +++ b/LICENCE @@ -0,0 +1,26 @@ +Copyright (c) 2023, Dennis Eriksen + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +1. Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + +2. Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +3. Neither the name of the copyright holder nor the names of its + contributors may be used to endorse or promote products derived from + this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/README.md b/README.md new file mode 100644 index 0000000..73d6484 --- /dev/null +++ b/README.md @@ -0,0 +1,14 @@ +# purl-rs +A simple URL-shortener in Rust. + +I created this URL-shortener because it turned out that my previous one, `purl`, +which was written i perl, was impractical to run in a `chroot` environment. + +This new one, written in [Rust](https://www.rust-lang.org/), has far fewer +dependencies to worry about in a `chroot` environment. It is written as a +replacement for the old `purl`, and therefor uses +[CGI](https://en.wikipedia.org/wiki/Common_Gateway_Interface). + +I use Nginx as my web-proxy, and run the cgi-binaries through +[slowcgi(8)](https://man.openbsd.org/slowcgi). See `nginx.conf` for +example-configuration. diff --git a/nginx.conf b/nginx.conf new file mode 100644 index 0000000..5a1c5e3 --- /dev/null +++ b/nginx.conf @@ -0,0 +1,35 @@ + # This needs to be included in a server{}-block. + # The basic-auth-file can be generated using `htpass -c file username`. + + location /form { + auth_basic "purl-rs"; + auth_basic_user_file /htpasswd/purl-rs; + + include fastcgi_params; + fastcgi_split_path_info ^(/)(.*); + fastcgi_param PATH_INFO $fastcgi_path_info; + fastcgi_param SCRIPT_FILENAME /cgi-bin/purl-rs/purl-rs; + fastcgi_param REMOTE_USER $remote_user; + fastcgi_pass unix:/run/slowcgi.sock; + } + + location /create { + auth_basic "purl-rs"; + auth_basic_user_file /htpasswd/purl-rs; + + include fastcgi_params; + fastcgi_split_path_info ^(/)(.*); + fastcgi_param PATH_INFO $fastcgi_path_info; + fastcgi_param SCRIPT_FILENAME /cgi-bin/purl-rs/purl-rs; + fastcgi_param REMOTE_USER $remote_user; + fastcgi_pass unix:/run/slowcgi.sock; + } + + location ~ ^/\+[a-zA-Z0-9_-]+$ { + include fastcgi_params; + fastcgi_split_path_info ^(/)(.*); + fastcgi_param PATH_INFO $fastcgi_path_info; + fastcgi_param SCRIPT_FILENAME /cgi-bin/purl-rs/purl-rs; + fastcgi_pass unix:/run/slowcgi.sock; + } + diff --git a/sample.env b/sample.env new file mode 100644 index 0000000..1eab738 --- /dev/null +++ b/sample.env @@ -0,0 +1,16 @@ +# Sample .env-file +# Put your .env-file right next to your purl-rs binary + +# DATABASE_URL - database details +#DATABASE_URL='postgresql://purl-rs:password@host.example.com/purl-rs' +DATABASE_URL='postgresql://localhost/purl-rs' + +# SHORT_URI_PREFIX - what separates host and the short. I.e. '/+' in the +# shortened url "example.com/+r83M" +SHORT_URI_PREFIX='/+' + +# FORM_URI - path that should display the form +FORM_URI='/form' + +# CREATE_URI - path to send requests to create shortened urls +CREATE_URI='/create' diff --git a/schema.sql b/schema.sql new file mode 100644 index 0000000..1089767 --- /dev/null +++ b/schema.sql @@ -0,0 +1,131 @@ +-- +-- PostgreSQL database dump +-- + +-- Dumped from database version 11.5 (Ubuntu 11.5-1) +-- Dumped by pg_dump version 11.5 (Ubuntu 11.5-1) + +SET statement_timeout = 0; +SET lock_timeout = 0; +SET idle_in_transaction_session_timeout = 0; +SET client_encoding = 'UTF8'; +SET standard_conforming_strings = on; +SELECT pg_catalog.set_config('search_path', '', false); +SET check_function_bodies = false; +SET xmloption = content; +SET client_min_messages = warning; +SET row_security = off; + +-- +-- Name: purl-rs; Type: DATABASE; Schema: -; Owner: postgres +-- + +CREATE DATABASE purl-rs WITH TEMPLATE = template0 ENCODING = 'UTF8' LC_COLLATE = 'en_IE.UTF-8' LC_CTYPE = 'en_IE.UTF-8'; + + +ALTER DATABASE purl-rs OWNER TO postgres; + +\connect purl-rs + +SET statement_timeout = 0; +SET lock_timeout = 0; +SET idle_in_transaction_session_timeout = 0; +SET client_encoding = 'UTF8'; +SET standard_conforming_strings = on; +SELECT pg_catalog.set_config('search_path', '', false); +SET check_function_bodies = false; +SET xmloption = content; +SET client_min_messages = warning; +SET row_security = off; + +SET default_tablespace = ''; + +SET default_with_oids = false; + +-- +-- Name: shorts; Type: TABLE; Schema: public; Owner: postgres +-- + +CREATE TABLE public.shorts ( + id integer NOT NULL, + url text NOT NULL, + short character varying NOT NULL, + created timestamp with time zone DEFAULT now() NOT NULL, + created_by character varying, + count integer DEFAULT 0, + last_visited timestamp with time zone +); + + +ALTER TABLE public.shorts OWNER TO postgres; + +-- +-- Name: shorts_id_seq; Type: SEQUENCE; Schema: public; Owner: postgres +-- + +CREATE SEQUENCE public.shorts_id_seq + AS integer + START WITH 1 + INCREMENT BY 1 + NO MINVALUE + NO MAXVALUE + CACHE 1; + + +ALTER TABLE public.shorts_id_seq OWNER TO postgres; + +-- +-- Name: shorts_id_seq; Type: SEQUENCE OWNED BY; Schema: public; Owner: postgres +-- + +ALTER SEQUENCE public.shorts_id_seq OWNED BY public.shorts.id; + + +-- +-- Name: shorts id; Type: DEFAULT; Schema: public; Owner: postgres +-- + +ALTER TABLE ONLY public.shorts ALTER COLUMN id SET DEFAULT nextval('public.shorts_id_seq'::regclass); + + +-- +-- Name: shorts shorts_pkey; Type: CONSTRAINT; Schema: public; Owner: postgres +-- + +ALTER TABLE ONLY public.shorts + ADD CONSTRAINT shorts_pkey PRIMARY KEY (id); + + +-- +-- Name: shorts shorts_short_key; Type: CONSTRAINT; Schema: public; Owner: postgres +-- + +ALTER TABLE ONLY public.shorts + ADD CONSTRAINT shorts_short_key UNIQUE (short); + + +-- +-- Name: DATABASE purl-rs; Type: ACL; Schema: -; Owner: postgres +-- + +GRANT CONNECT ON DATABASE purl-rs TO "www"; + + +-- +-- Name: TABLE shorts; Type: ACL; Schema: public; Owner: postgres +-- + +GRANT SELECT,INSERT,UPDATE ON TABLE public.shorts TO "www"; + + +-- +-- Name: SEQUENCE shorts_id_seq; Type: ACL; Schema: public; Owner: postgres +-- + +GRANT SELECT,USAGE ON SEQUENCE public.shorts_id_seq TO "www"; + + +-- +-- PostgreSQL database dump complete +-- + diff --git a/src/main.rs b/src/main.rs index 8dd0f93..638a9a0 100644 --- a/src/main.rs +++ b/src/main.rs @@ -24,11 +24,11 @@ use url::Url; // Do the dirty fn main() { - // Get variables from dotenv - let dburl:&str = &dotenv::var("DATABASE_URL").unwrap(); + // Get variables from dotenv, or use defaults + let dburl:&str = &dotenv::var("DATABASE_URL").unwrap_or("postgresql://localhost/purl-rs".to_string()); let create_uri:&str = &dotenv::var("CREATE_URI").unwrap_or("/create".to_string()); let form_uri:&str = &dotenv::var("FORM_URI").unwrap_or("/form".to_string()); - let short_uri_prefix:&str = &dotenv::var("SHORT_URI_PREFIX").unwrap_or("/".to_string()); + let short_uri_prefix:&str = &dotenv::var("SHORT_URI_PREFIX").unwrap_or("/+".to_string()); // Connect to db let mut db = Client::connect(dburl, NoTls).unwrap(); -- cgit v1.2.3