Added spectrogram generator with python
This commit is contained in:
parent
8192e30810
commit
33e2beb52d
69
composer.lock
generated
Normal file
69
composer.lock
generated
Normal file
@ -0,0 +1,69 @@
|
||||
{
|
||||
"_readme": [
|
||||
"This file locks the dependencies of your project to a known state",
|
||||
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
||||
"This file is @generated automatically"
|
||||
],
|
||||
"content-hash": "f493960dbf3229f8998effb35c5e910d",
|
||||
"packages": [
|
||||
{
|
||||
"name": "erusev/parsedown",
|
||||
"version": "1.7.4",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/erusev/parsedown.git",
|
||||
"reference": "cb17b6477dfff935958ba01325f2e8a2bfa6dab3"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/erusev/parsedown/zipball/cb17b6477dfff935958ba01325f2e8a2bfa6dab3",
|
||||
"reference": "cb17b6477dfff935958ba01325f2e8a2bfa6dab3",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"ext-mbstring": "*",
|
||||
"php": ">=5.3.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "^4.8.35"
|
||||
},
|
||||
"type": "library",
|
||||
"autoload": {
|
||||
"psr-0": {
|
||||
"Parsedown": ""
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Emanuil Rusev",
|
||||
"email": "hello@erusev.com",
|
||||
"homepage": "http://erusev.com"
|
||||
}
|
||||
],
|
||||
"description": "Parser for Markdown.",
|
||||
"homepage": "http://parsedown.org",
|
||||
"keywords": [
|
||||
"markdown",
|
||||
"parser"
|
||||
],
|
||||
"support": {
|
||||
"issues": "https://github.com/erusev/parsedown/issues",
|
||||
"source": "https://github.com/erusev/parsedown/tree/1.7.x"
|
||||
},
|
||||
"time": "2019-12-30T22:54:17+00:00"
|
||||
}
|
||||
],
|
||||
"packages-dev": [],
|
||||
"aliases": [],
|
||||
"minimum-stability": "stable",
|
||||
"stability-flags": [],
|
||||
"prefer-stable": false,
|
||||
"prefer-lowest": false,
|
||||
"platform": [],
|
||||
"platform-dev": [],
|
||||
"plugin-api-version": "2.0.0"
|
||||
}
|
5
public/composer.json
Normal file
5
public/composer.json
Normal file
@ -0,0 +1,5 @@
|
||||
{
|
||||
"require": {
|
||||
"erusev/parsedown": "^1.7"
|
||||
}
|
||||
}
|
71
public/database/authors.sql
Normal file
71
public/database/authors.sql
Normal file
@ -0,0 +1,71 @@
|
||||
-- phpMyAdmin SQL Dump
|
||||
-- version 5.1.0
|
||||
-- https://www.phpmyadmin.net/
|
||||
--
|
||||
-- Host: localhost
|
||||
-- Generation Time: Mar 30, 2021 at 01:11 PM
|
||||
-- Server version: 10.5.9-MariaDB
|
||||
-- PHP Version: 7.4.17RC1
|
||||
|
||||
SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
|
||||
START TRANSACTION;
|
||||
SET time_zone = "+00:00";
|
||||
|
||||
|
||||
/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
|
||||
/*!40101 SET NAMES utf8mb4 */;
|
||||
|
||||
--
|
||||
-- Database: `chirocanto`
|
||||
--
|
||||
|
||||
-- --------------------------------------------------------
|
||||
|
||||
--
|
||||
-- Table structure for table `authors`
|
||||
--
|
||||
|
||||
CREATE TABLE `authors` (
|
||||
`id` int(11) NOT NULL,
|
||||
`firstname` varchar(125) NOT NULL,
|
||||
`lastname` varchar(125) NOT NULL,
|
||||
`username` varchar(25) NOT NULL,
|
||||
`email` varchar(125) NOT NULL,
|
||||
`website` varchar(125) NOT NULL,
|
||||
`password` varchar(125) NOT NULL,
|
||||
`entry_timestamp` timestamp NOT NULL DEFAULT current_timestamp()
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
|
||||
|
||||
--
|
||||
-- Dumping data for table `authors`
|
||||
--
|
||||
|
||||
INSERT INTO `authors` (`id`, `firstname`, `lastname`, `username`, `email`, `website`, `password`, `entry_timestamp`) VALUES
|
||||
(9, 'Samuel', 'ORTION', 'UncleSamulus', 'samuel.ortion@orange.fr', 'https://samuel.ortion.xyz', '$2y$10$31D2YXTFzhUM9gLDcXXEvuzp4EKN3DFv7No5G8/wXE1rUuDgu8mUO', '2021-03-29 17:21:59');
|
||||
|
||||
--
|
||||
-- Indexes for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- Indexes for table `authors`
|
||||
--
|
||||
ALTER TABLE `authors`
|
||||
ADD PRIMARY KEY (`id`);
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for table `authors`
|
||||
--
|
||||
ALTER TABLE `authors`
|
||||
MODIFY `id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=10;
|
||||
COMMIT;
|
||||
|
||||
/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
|
66
public/database/categories.sql
Normal file
66
public/database/categories.sql
Normal file
@ -0,0 +1,66 @@
|
||||
-- phpMyAdmin SQL Dump
|
||||
-- version 5.1.0
|
||||
-- https://www.phpmyadmin.net/
|
||||
--
|
||||
-- Host: localhost
|
||||
-- Generation Time: Mar 30, 2021 at 01:11 PM
|
||||
-- Server version: 10.5.9-MariaDB
|
||||
-- PHP Version: 7.4.17RC1
|
||||
|
||||
SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
|
||||
START TRANSACTION;
|
||||
SET time_zone = "+00:00";
|
||||
|
||||
|
||||
/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
|
||||
/*!40101 SET NAMES utf8mb4 */;
|
||||
|
||||
--
|
||||
-- Database: `chirocanto`
|
||||
--
|
||||
|
||||
-- --------------------------------------------------------
|
||||
|
||||
--
|
||||
-- Table structure for table `categories`
|
||||
--
|
||||
|
||||
CREATE TABLE `categories` (
|
||||
`id` int(11) NOT NULL,
|
||||
`cat_name` varchar(125) NOT NULL,
|
||||
`cat_description` varchar(125) NOT NULL
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
|
||||
|
||||
--
|
||||
-- Dumping data for table `categories`
|
||||
--
|
||||
|
||||
INSERT INTO `categories` (`id`, `cat_name`, `cat_description`) VALUES
|
||||
(1, 'Records', 'Topics related to uploaded records.');
|
||||
|
||||
--
|
||||
-- Indexes for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- Indexes for table `categories`
|
||||
--
|
||||
ALTER TABLE `categories`
|
||||
ADD PRIMARY KEY (`id`);
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for table `categories`
|
||||
--
|
||||
ALTER TABLE `categories`
|
||||
MODIFY `id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=2;
|
||||
COMMIT;
|
||||
|
||||
/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
|
78
public/database/records.sql
Normal file
78
public/database/records.sql
Normal file
@ -0,0 +1,78 @@
|
||||
-- phpMyAdmin SQL Dump
|
||||
-- version 5.1.0
|
||||
-- https://www.phpmyadmin.net/
|
||||
--
|
||||
-- Host: localhost
|
||||
-- Generation Time: Mar 30, 2021 at 01:11 PM
|
||||
-- Server version: 10.5.9-MariaDB
|
||||
-- PHP Version: 7.4.17RC1
|
||||
|
||||
SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
|
||||
START TRANSACTION;
|
||||
SET time_zone = "+00:00";
|
||||
|
||||
|
||||
/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
|
||||
/*!40101 SET NAMES utf8mb4 */;
|
||||
|
||||
--
|
||||
-- Database: `chirocanto`
|
||||
--
|
||||
|
||||
-- --------------------------------------------------------
|
||||
|
||||
--
|
||||
-- Table structure for table `records`
|
||||
--
|
||||
|
||||
CREATE TABLE `records` (
|
||||
`id` int(11) NOT NULL,
|
||||
`entry_timestamp` bigint(11) NOT NULL DEFAULT current_timestamp(),
|
||||
`author_id` int(11) NOT NULL,
|
||||
`recordist_name` varchar(125) NOT NULL,
|
||||
`file_name` varchar(125) NOT NULL,
|
||||
`license` varchar(25) NOT NULL,
|
||||
`species` varchar(125) NOT NULL,
|
||||
`subspecies` varchar(125) NOT NULL,
|
||||
`sound_type` varchar(25) NOT NULL,
|
||||
`country` varchar(125) NOT NULL,
|
||||
`lat` varchar(20) NOT NULL,
|
||||
`lng` varchar(20) NOT NULL,
|
||||
`date` date NOT NULL,
|
||||
`time` time NOT NULL,
|
||||
`remarks` text NOT NULL
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
|
||||
|
||||
--
|
||||
-- Dumping data for table `records`
|
||||
--
|
||||
|
||||
INSERT INTO `records` (`id`, `entry_timestamp`, `author_id`, `recordist_name`, `file_name`, `license`, `species`, `subspecies`, `sound_type`, `country`, `lat`, `lng`, `date`, `time`, `remarks`) VALUES
|
||||
(2, 20210330072954, 9, 'Samuel ORTION', 'PaRecAR628069_20200526_040726.wav', 'CC-by-nc-sa-4.0', 'Pipistrellus kuhlii', '', 'echolocation', 'France', '47.87840601525087', ' 0.21813243633005192', '2020-05-26', '04:07:00', '');
|
||||
|
||||
--
|
||||
-- Indexes for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- Indexes for table `records`
|
||||
--
|
||||
ALTER TABLE `records`
|
||||
ADD PRIMARY KEY (`id`);
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for table `records`
|
||||
--
|
||||
ALTER TABLE `records`
|
||||
MODIFY `id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=3;
|
||||
COMMIT;
|
||||
|
||||
/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
|
81
public/database/replies.sql
Normal file
81
public/database/replies.sql
Normal file
@ -0,0 +1,81 @@
|
||||
-- phpMyAdmin SQL Dump
|
||||
-- version 5.1.0
|
||||
-- https://www.phpmyadmin.net/
|
||||
--
|
||||
-- Host: localhost
|
||||
-- Generation Time: Mar 30, 2021 at 01:12 PM
|
||||
-- Server version: 10.5.9-MariaDB
|
||||
-- PHP Version: 7.4.17RC1
|
||||
|
||||
SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
|
||||
START TRANSACTION;
|
||||
SET time_zone = "+00:00";
|
||||
|
||||
|
||||
/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
|
||||
/*!40101 SET NAMES utf8mb4 */;
|
||||
|
||||
--
|
||||
-- Database: `chirocanto`
|
||||
--
|
||||
|
||||
-- --------------------------------------------------------
|
||||
|
||||
--
|
||||
-- Table structure for table `replies`
|
||||
--
|
||||
|
||||
CREATE TABLE `replies` (
|
||||
`id` int(11) NOT NULL,
|
||||
`reply_content` text NOT NULL,
|
||||
`reply_date` datetime NOT NULL DEFAULT current_timestamp(),
|
||||
`reply_topic` int(8) NOT NULL,
|
||||
`reply_by` int(8) NOT NULL
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
|
||||
|
||||
--
|
||||
-- Dumping data for table `replies`
|
||||
--
|
||||
|
||||
INSERT INTO `replies` (`id`, `reply_content`, `reply_date`, `reply_topic`, `reply_by`) VALUES
|
||||
(1, 'It is probably better a *Pipistrellus pipistrellus*.', '2021-03-30 13:56:01', 1, 9);
|
||||
|
||||
--
|
||||
-- Indexes for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- Indexes for table `replies`
|
||||
--
|
||||
ALTER TABLE `replies`
|
||||
ADD PRIMARY KEY (`id`),
|
||||
ADD KEY `reply_topic` (`reply_topic`),
|
||||
ADD KEY `reply_by` (`reply_by`);
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for table `replies`
|
||||
--
|
||||
ALTER TABLE `replies`
|
||||
MODIFY `id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=2;
|
||||
|
||||
--
|
||||
-- Constraints for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- Constraints for table `replies`
|
||||
--
|
||||
ALTER TABLE `replies`
|
||||
ADD CONSTRAINT `replies_ibfk_1` FOREIGN KEY (`reply_topic`) REFERENCES `topics` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,
|
||||
ADD CONSTRAINT `replies_ibfk_2` FOREIGN KEY (`reply_by`) REFERENCES `authors` (`id`) ON UPDATE CASCADE;
|
||||
COMMIT;
|
||||
|
||||
/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
|
81
public/database/topics.sql
Normal file
81
public/database/topics.sql
Normal file
@ -0,0 +1,81 @@
|
||||
-- phpMyAdmin SQL Dump
|
||||
-- version 5.1.0
|
||||
-- https://www.phpmyadmin.net/
|
||||
--
|
||||
-- Host: localhost
|
||||
-- Generation Time: Mar 30, 2021 at 01:12 PM
|
||||
-- Server version: 10.5.9-MariaDB
|
||||
-- PHP Version: 7.4.17RC1
|
||||
|
||||
SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
|
||||
START TRANSACTION;
|
||||
SET time_zone = "+00:00";
|
||||
|
||||
|
||||
/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
|
||||
/*!40101 SET NAMES utf8mb4 */;
|
||||
|
||||
--
|
||||
-- Database: `chirocanto`
|
||||
--
|
||||
|
||||
-- --------------------------------------------------------
|
||||
|
||||
--
|
||||
-- Table structure for table `topics`
|
||||
--
|
||||
|
||||
CREATE TABLE `topics` (
|
||||
`id` int(11) NOT NULL,
|
||||
`topic_subject` varchar(255) NOT NULL,
|
||||
`topic_date` datetime NOT NULL DEFAULT current_timestamp(),
|
||||
`topic_cat` int(8) NOT NULL,
|
||||
`topic_by` int(8) NOT NULL
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
|
||||
|
||||
--
|
||||
-- Dumping data for table `topics`
|
||||
--
|
||||
|
||||
INSERT INTO `topics` (`id`, `topic_subject`, `topic_date`, `topic_cat`, `topic_by`) VALUES
|
||||
(1, 'Pipistrellus kuhlii record', '2021-03-30 11:42:08', 1, 9);
|
||||
|
||||
--
|
||||
-- Indexes for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- Indexes for table `topics`
|
||||
--
|
||||
ALTER TABLE `topics`
|
||||
ADD PRIMARY KEY (`id`),
|
||||
ADD KEY `topic_cat` (`topic_cat`),
|
||||
ADD KEY `topic_by` (`topic_by`);
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- AUTO_INCREMENT for table `topics`
|
||||
--
|
||||
ALTER TABLE `topics`
|
||||
MODIFY `id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=2;
|
||||
|
||||
--
|
||||
-- Constraints for dumped tables
|
||||
--
|
||||
|
||||
--
|
||||
-- Constraints for table `topics`
|
||||
--
|
||||
ALTER TABLE `topics`
|
||||
ADD CONSTRAINT `topics_ibfk_1` FOREIGN KEY (`topic_cat`) REFERENCES `categories` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,
|
||||
ADD CONSTRAINT `topics_ibfk_2` FOREIGN KEY (`topic_by`) REFERENCES `authors` (`id`) ON UPDATE CASCADE;
|
||||
COMMIT;
|
||||
|
||||
/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
|
||||
/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
|
||||
/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
|
@ -3,6 +3,7 @@ ini_set('display_errors', 1);
|
||||
ini_set('display_startup_errors', 1);
|
||||
error_reporting(E_ALL);
|
||||
$root = realpath($_SERVER["DOCUMENT_ROOT"]);
|
||||
include("$root/vendor/erusev/parsedown/Parsedown.php");
|
||||
|
||||
require "$root/database/credentials.php";
|
||||
// Connect the database
|
||||
@ -18,6 +19,8 @@ try{
|
||||
$req = $db->prepare('SELECT * FROM `categories`');
|
||||
$req->execute();
|
||||
$rows = $req->fetchAll(PDO::FETCH_ASSOC);
|
||||
|
||||
$Parsedown = new Parsedown();
|
||||
?>
|
||||
<h3>Categories</h3>
|
||||
<table id="categories">
|
||||
@ -30,11 +33,12 @@ $rows = $req->fetchAll(PDO::FETCH_ASSOC);
|
||||
<tbody>
|
||||
<?php
|
||||
foreach ($rows as $row) {
|
||||
?>
|
||||
<tr>
|
||||
<td><?=$row['cat_name']?></td>
|
||||
<td><?=$row['cat_description']?></td>
|
||||
</tr>
|
||||
?>
|
||||
<tr>
|
||||
|
||||
<td><a href="newtopic.php?cat=<?=$row['id']?>"><?=$row['cat_name']?></a></td></p>
|
||||
<td><?=$Parsedown->text($row['cat_description'])?></td>
|
||||
</tr>
|
||||
<?php
|
||||
}
|
||||
?> </tbody>
|
||||
@ -44,6 +48,6 @@ foreach ($rows as $row) {
|
||||
<label for="title">Category title</label>
|
||||
<input type="text" id="title" name="title" placeholder="Enter a name for the new category.." required>
|
||||
<label for="description">Category description</label>
|
||||
<textarea name="description" id="description" cols="30" rows="10" placeholder="Enter a description for the new category.." required></textarea>
|
||||
<textarea name="description" id="description" cols="30" rows="5" placeholder="Enter a description for the new category (support Markdown).." required></textarea>
|
||||
<input type="submit" value="submit" name="submit"><input type="reset" value="reset">
|
||||
</form>
|
||||
|
84
public/forum/createtopic.php
Normal file
84
public/forum/createtopic.php
Normal file
@ -0,0 +1,84 @@
|
||||
<?php
|
||||
function create_topic($topic_subject, $topic_cat, $topic_by)
|
||||
{
|
||||
$root = realpath($_SERVER["DOCUMENT_ROOT"]);
|
||||
require "$root/database/credentials.php";
|
||||
// Connect the database
|
||||
try{
|
||||
$db = new PDO("mysql:host=$host;dbname=$database;charset=utf8",
|
||||
$user,
|
||||
$password,
|
||||
array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION
|
||||
));
|
||||
}catch (Exception $e){
|
||||
die("Error : ".$e->getMessage());
|
||||
}
|
||||
$req = $db->prepare('INSERT INTO `topics` (topic_subject, topic_date, topic_cat, topic_by) VALUES (:topic_subject, now(), :topic_cat, :topic_by)');
|
||||
$req->execute(array(
|
||||
"topic_subject"=>$topic_subject,
|
||||
"topic_cat"=>$topic_cat,
|
||||
"topic_by"=>$topic_by
|
||||
));
|
||||
}
|
||||
|
||||
ini_set('display_errors', 1);
|
||||
ini_set('display_startup_errors', 1);
|
||||
error_reporting(E_ALL);
|
||||
session_start();
|
||||
|
||||
$_SESSION['error_msg'] = "";
|
||||
if (isset($_POST['submit']))
|
||||
{
|
||||
if (isset($_SESSION['username'])) {
|
||||
|
||||
$root = realpath($_SERVER["DOCUMENT_ROOT"]);
|
||||
require "$root/database/credentials.php";
|
||||
// Connect the database
|
||||
try{
|
||||
$db = new PDO("mysql:host=$host;dbname=$database;charset=utf8",
|
||||
$user,
|
||||
$password,
|
||||
array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION
|
||||
));
|
||||
}catch (Exception $e){
|
||||
die("Error : ".$e->getMessage());
|
||||
}
|
||||
$req = $db->prepare('SELECT id FROM authors WHERE username=:username');
|
||||
$req->execute(array(
|
||||
"username"=>$_SESSION['username']
|
||||
));
|
||||
if ($data = $req->fetch())
|
||||
{
|
||||
$user_id = $data['id'];
|
||||
}
|
||||
if (isset($_POST['topic_subject']))
|
||||
{
|
||||
$topic_subject = $_POST['topic_subject'];
|
||||
} else
|
||||
{
|
||||
$_SESSION['error_msg'] .= "You did not enter a proper topic subject. \n";
|
||||
}
|
||||
if (isset($_POST['category']))
|
||||
{
|
||||
$id_cat = $_POST['category'];
|
||||
} else
|
||||
{
|
||||
$_SESSION['error_msg'] .= "You did not enter a proper topic category. \n";
|
||||
}
|
||||
} else {
|
||||
$_SESSION['error_msg'] .= "You did not log in.\n";
|
||||
header('Location: '."/auth/login/");
|
||||
}
|
||||
} else
|
||||
{
|
||||
$_SESSION['error_msg'] .= "You did not sumit the category creation form.\n";
|
||||
}
|
||||
|
||||
if ($_SESSION['error_msg'] == "")
|
||||
{
|
||||
create_topic($topic_subject, $id_cat, $user_id);
|
||||
header('Location: '."/forum");
|
||||
} else {
|
||||
header('Location: '."/auth/login/");
|
||||
}
|
||||
?>
|
@ -13,7 +13,7 @@ $root = realpath($_SERVER["DOCUMENT_ROOT"]);
|
||||
<meta charset="UTF-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Chiro - Canto</title>
|
||||
<title>Forum | Chiro - Canto</title>
|
||||
<link rel="stylesheet" type="text/css" href="/styles/style.css">
|
||||
</head>
|
||||
<body>
|
||||
|
56
public/forum/newtopic.php
Normal file
56
public/forum/newtopic.php
Normal file
@ -0,0 +1,56 @@
|
||||
<?php
|
||||
ini_set('display_errors', 1);
|
||||
ini_set('display_startup_errors', 1);
|
||||
error_reporting(E_ALL);
|
||||
session_start();
|
||||
$root = realpath($_SERVER["DOCUMENT_ROOT"]);
|
||||
|
||||
require "$root/database/credentials.php";
|
||||
// Connect the database
|
||||
try{
|
||||
$db = new PDO("mysql:host=$host;dbname=$database;charset=utf8",
|
||||
$user,
|
||||
$password,
|
||||
array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION
|
||||
));
|
||||
}catch (Exception $e){
|
||||
die("Error : ".$e->getMessage());
|
||||
}
|
||||
$req = $db->prepare('SELECT cat_name, cat_description FROM `categories` WHERE id=:id');
|
||||
$req->execute(array(
|
||||
"id"=>$_GET['cat']
|
||||
));
|
||||
if ($data = $req->fetch())
|
||||
{
|
||||
$cat_name = $data['cat_name'];
|
||||
$cat_description = $data['cat_description'];
|
||||
}
|
||||
?>
|
||||
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Chiro - Canto</title>
|
||||
<link rel="stylesheet" type="text/css" href="/styles/style.css">
|
||||
</head>
|
||||
<body>
|
||||
<?php include("$root/menu.php");?>
|
||||
<?php include("$root/header.php");?>
|
||||
<section>
|
||||
<h2>Forum</h2>
|
||||
<h3>Create a new topic <?=isset($cat_name) ? "in ".$cat_name : ""?></h3>
|
||||
<form action="createtopic.php" method="post">
|
||||
<label for="topic">Topic subject</label>
|
||||
<input type="text" name="topic_subject" id="topic" placeholder="Enter a topic subject.." required>
|
||||
<label for="category">Topic category</label>
|
||||
<input type="number" id="category" name="category" value="<?=$_GET['cat']?>" required>
|
||||
<input type="submit" value="submit" name="submit"><input type="reset" value="reset">
|
||||
</form>
|
||||
</section>
|
||||
<?php include("$root/footer.php");?>
|
||||
</body>
|
||||
<script src="/scripts/script.js"></script>
|
||||
</html>
|
29
public/forum/topics/index.php
Normal file
29
public/forum/topics/index.php
Normal file
@ -0,0 +1,29 @@
|
||||
<?php
|
||||
ini_set('display_errors', 1);
|
||||
ini_set('display_startup_errors', 1);
|
||||
error_reporting(E_ALL);
|
||||
session_start();
|
||||
$root = realpath($_SERVER["DOCUMENT_ROOT"]);
|
||||
|
||||
?>
|
||||
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Forum | Chiro - Canto</title>
|
||||
<link rel="stylesheet" type="text/css" href="/styles/style.css">
|
||||
</head>
|
||||
<body>
|
||||
<?php include("$root/menu.php");?>
|
||||
<?php include("$root/header.php");?>
|
||||
<section>
|
||||
<h2>Forum</h2>
|
||||
<?php include("topics.php");?>
|
||||
</section>
|
||||
<?php include("$root/footer.php");?>
|
||||
</body>
|
||||
<script src="/scripts/script.js"></script>
|
||||
</html>
|
71
public/forum/topics/sendreply.php
Normal file
71
public/forum/topics/sendreply.php
Normal file
@ -0,0 +1,71 @@
|
||||
<?php
|
||||
function send_reply($reply_content, $topic_id, $reply_by)
|
||||
{
|
||||
$root = realpath($_SERVER["DOCUMENT_ROOT"]);
|
||||
require "$root/database/credentials.php";
|
||||
// Connect the database
|
||||
try{
|
||||
$db = new PDO("mysql:host=$host;dbname=$database;charset=utf8",
|
||||
$user,
|
||||
$password,
|
||||
array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION
|
||||
));
|
||||
}catch (Exception $e){
|
||||
die("Error : ".$e->getMessage());
|
||||
}
|
||||
$req = $db->prepare('SELECT id FROM `authors`WHERE username=:username');
|
||||
$req->execute(array(
|
||||
"username"=>$reply_by
|
||||
));
|
||||
if ($data=$req->fetch())
|
||||
{
|
||||
$user_id = $data['id'];
|
||||
}
|
||||
$req = $db->prepare('INSERT INTO `replies` (reply_content, reply_date, reply_topic, reply_by) VALUES (:reply_content, now(), :reply_topic, :reply_by)');
|
||||
$req->execute(array(
|
||||
"reply_content"=>$reply_content,
|
||||
"reply_topic"=>$topic_id,
|
||||
"reply_by"=>$user_id
|
||||
));
|
||||
}
|
||||
|
||||
ini_set('display_errors', 1);
|
||||
ini_set('display_startup_errors', 1);
|
||||
error_reporting(E_ALL);
|
||||
session_start();
|
||||
|
||||
$_SESSION['error_msg'] = "";
|
||||
if (isset($_POST['submit']))
|
||||
{
|
||||
if (isset($_SESSION['username'])) {
|
||||
if (isset($_POST['topic_id']))
|
||||
{
|
||||
$topic_id = $_POST['topic_id'];
|
||||
} else
|
||||
{
|
||||
$_SESSION['error_msg'] .= "You did not enter your reply. \n";
|
||||
}
|
||||
if (isset($_POST['reply']))
|
||||
{
|
||||
$reply_content = $_POST['reply'];
|
||||
} else
|
||||
{
|
||||
$_SESSION['error_msg'] .= "You did not enter your reply. \n";
|
||||
}
|
||||
} else {
|
||||
$_SESSION['error_msg'] .= "You did not log in.\n";
|
||||
header('Location: '."/auth/login/");
|
||||
}
|
||||
} else
|
||||
{
|
||||
$_SESSION['error_msg'] .= "You did not sumit the reply form.\n";
|
||||
}
|
||||
|
||||
if ($_SESSION['error_msg'] == "")
|
||||
{
|
||||
send_reply($reply_content, $topic_id, $_SESSION['username']);
|
||||
header('Location: '."/forum/topics/?topic$topic_id");
|
||||
} else {
|
||||
header('Location: '."/auth/login/");
|
||||
}
|
||||
?>
|
130
public/forum/topics/topics.php
Normal file
130
public/forum/topics/topics.php
Normal file
@ -0,0 +1,130 @@
|
||||
<?php
|
||||
ini_set('display_errors', 1);
|
||||
ini_set('display_startup_errors', 1);
|
||||
error_reporting(E_ALL);
|
||||
$root = realpath($_SERVER["DOCUMENT_ROOT"]);
|
||||
include("$root/../vendor/erusev/parsedown/Parsedown.php");
|
||||
$Parsedown = new Parsedown();
|
||||
require "$root/database/credentials.php";
|
||||
// Connect the database
|
||||
try{
|
||||
$db = new PDO("mysql:host=$host;dbname=$database;charset=utf8",
|
||||
$user,
|
||||
$password,
|
||||
array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION
|
||||
));
|
||||
}catch (Exception $e){
|
||||
die("Error : ".$e->getMessage());
|
||||
}
|
||||
|
||||
if (isset($_GET['topic'])){
|
||||
$topic_id = $_GET['topic'];
|
||||
$req = $db->prepare('SELECT topic_subject FROM topics WHERE id=:id');
|
||||
$req->execute(array(
|
||||
"id"=>$topic_id
|
||||
));
|
||||
if ($data = $req->fetch())
|
||||
{
|
||||
$subject = $data['topic_subject'];
|
||||
}
|
||||
$req = $db->prepare('SELECT * FROM replies WHERE reply_topic=:id_topic');
|
||||
$req->execute(array(
|
||||
"id_topic"=>$topic_id
|
||||
));
|
||||
try {
|
||||
$rows = $req->fetchAll(PDO::FETCH_ASSOC);
|
||||
?>
|
||||
<h3><?=$subject?></h3>
|
||||
<table id="replies">
|
||||
<thead>
|
||||
<tr>
|
||||
<th scope="col">Author</th>
|
||||
<th scope="col">Reply</th>
|
||||
<th scope="col">Date</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<?php
|
||||
foreach ($rows as $row) {
|
||||
$reply_by = $row['reply_by'];
|
||||
$req = $db->prepare('SELECT firstname, lastname, username FROM `authors` WHERE id=:user_id');
|
||||
$req->execute(array(
|
||||
"user_id"=>$reply_by
|
||||
));
|
||||
if ($data = $req->fetch())
|
||||
{
|
||||
$username = $data['username'];
|
||||
$firstname = $data['firstname'];
|
||||
$lastname = $data['lastname'];
|
||||
}
|
||||
?>
|
||||
<tr>
|
||||
<td><?="$firstname $lastname<br> ($username)"?></td>
|
||||
<td><?=$Parsedown->text($row['reply_content'])?></td>
|
||||
<td><?=$row['reply_date']?></td>
|
||||
</tr>
|
||||
<?php
|
||||
}
|
||||
?>
|
||||
</tbody>
|
||||
</table>
|
||||
<br>
|
||||
<form action="sendreply.php" method="post">
|
||||
<input type="hidden" name="topic_id" value="<?=$topic_id?>">
|
||||
<label for="reply">Your Reply</label>
|
||||
<textarea name="reply" id="reply" cols="30" rows="10" placeholder="Enter your reply (support Markdown).."></textarea>
|
||||
<input type="submit" name="submit" value="submit">
|
||||
<input type="reset" name="reset" value="reset">
|
||||
</form>
|
||||
<?php
|
||||
|
||||
} catch (Exception $e)
|
||||
{
|
||||
die("Error : ".$e->getMessage());
|
||||
echo "Can fetch topic data.\n";
|
||||
}
|
||||
}
|
||||
else {
|
||||
|
||||
$req = $db->prepare('SELECT * FROM `topics`');
|
||||
$req->execute();
|
||||
$rows = $req->fetchAll(PDO::FETCH_ASSOC);
|
||||
|
||||
?>
|
||||
<h3>Topics</h3>
|
||||
<table id="categories">
|
||||
<thead>
|
||||
<tr>
|
||||
<th scope="col">Subjects</th>
|
||||
<th scope="col">Answers</th>
|
||||
<th scope="col">Author</th>
|
||||
<th scope="col">Creation date</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<?php
|
||||
foreach ($rows as $row) {
|
||||
$topic_by = $row['topic_by'];
|
||||
$req = $db->prepare('SELECT firstname, lastname, username FROM `authors` WHERE id=:user_id');
|
||||
$req->execute(array(
|
||||
"user_id"=>$topic_by
|
||||
));
|
||||
if ($data = $req->fetch())
|
||||
{
|
||||
$username = $data['username'];
|
||||
$firstname = $data['firstname'];
|
||||
$lastname = $data['lastname'];
|
||||
}
|
||||
?>
|
||||
<tr>
|
||||
<td><a href="<?="?topic=".$row['id']?>"><?=$row['topic_subject']?></a></td>
|
||||
<td><?="To be completed"?></td>
|
||||
<td><?="$firstname $lastname ($username)"?></td>
|
||||
<td><?=$row['topic_date']?></td>
|
||||
</tr>
|
||||
<?php
|
||||
}
|
||||
?> </tbody>
|
||||
</table>
|
||||
<?php
|
||||
}
|
@ -13,40 +13,40 @@ win.onscroll = function() {
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* Link preview in nav bar
|
||||
*/
|
||||
nav = document.getElementsByTagName('nav')[0];
|
||||
navItems = nav.children[0].children;
|
||||
for (navItem of navItems) {
|
||||
console.log(navItem);
|
||||
navItem.addEventListener('mouseover', function() {
|
||||
displayPreview(this);
|
||||
});
|
||||
navItem.addEventListener('mouseleave', function() {
|
||||
hidePreview();
|
||||
})
|
||||
}
|
||||
// /*
|
||||
// * Link preview in nav bar
|
||||
// */
|
||||
// nav = document.getElementsByTagName('nav')[0];
|
||||
// navItems = nav.children[0].children;
|
||||
// for (navItem of navItems) {
|
||||
// console.log(navItem);
|
||||
// navItem.addEventListener('mouseover', function() {
|
||||
// displayPreview(this);
|
||||
// });
|
||||
// navItem.addEventListener('mouseleave', function() {
|
||||
// hidePreview();
|
||||
// })
|
||||
// }
|
||||
|
||||
let iframe = document.createElement('iframe');
|
||||
iframe.style.display = "none";
|
||||
nav.appendChild(iframe);
|
||||
// let iframe = document.createElement('iframe');
|
||||
// iframe.style.display = "none";
|
||||
// nav.appendChild(iframe);
|
||||
|
||||
function displayPreview(navItem) {
|
||||
let url = navItem.href;
|
||||
// console.log(url);
|
||||
iframe.src = url;
|
||||
iframe.id = "previewFrame";
|
||||
iframe.style.width = "600px";
|
||||
iframe.style.height = "600px";
|
||||
iframe.style.display = "block";
|
||||
iframe.style.position = "fixed";
|
||||
var x = event.clientX;
|
||||
// var y = event.clientY;
|
||||
iframe.style.top = 5 + 'em';
|
||||
iframe.style.left = (x - 50) + 'px';
|
||||
}
|
||||
// function displayPreview(navItem) {
|
||||
// let url = navItem.href;
|
||||
// // console.log(url);
|
||||
// iframe.src = url;
|
||||
// iframe.id = "previewFrame";
|
||||
// iframe.style.width = "600px";
|
||||
// iframe.style.height = "600px";
|
||||
// iframe.style.display = "block";
|
||||
// iframe.style.position = "fixed";
|
||||
// var x = event.clientX;
|
||||
// // var y = event.clientY;
|
||||
// iframe.style.top = 5 + 'em';
|
||||
// iframe.style.left = (x - 50) + 'px';
|
||||
// }
|
||||
|
||||
function hidePreview() {
|
||||
iframe.style.display = "none";
|
||||
}
|
||||
// function hidePreview() {
|
||||
// iframe.style.display = "none";
|
||||
// }
|
BIN
public/spectrogram3.png
Normal file
BIN
public/spectrogram3.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 103 KiB |
22
public/src/spectro.py
Normal file
22
public/src/spectro.py
Normal file
@ -0,0 +1,22 @@
|
||||
#import the pyplot and wavfile modules
|
||||
import matplotlib.pyplot as plt
|
||||
from scipy.io import wavfile
|
||||
# Read the wav file (mono)
|
||||
file = "Car721035-2020-Pass0-Z2-PaRecAR628069_20200725_005937_000.wav"
|
||||
file_path = f"/var/www/chiro-canto/public/storage/records/{file}"
|
||||
print(file)
|
||||
samplingFrequency, signalData = wavfile.read(file_path)
|
||||
# Plot the signal read from wav file
|
||||
# plt.subplot(211)
|
||||
# plt.title('Spectrogram of a wav file with piano music')
|
||||
# plt.plot(signalData)
|
||||
# plt.xlabel('Sample')
|
||||
# plt.ylabel('Amplitude')
|
||||
# plt.subplot(212)
|
||||
plt.specgram(signalData,Fs=samplingFrequency)
|
||||
# plt.xlabel('Time')
|
||||
# plt.ylabel('Frequency')
|
||||
plt.savefig(f'/var/www/chiro-canto/public/storage/records/{file}')
|
||||
plt.show()
|
||||
|
||||
|
19
public/src/spectro_cli.py
Normal file
19
public/src/spectro_cli.py
Normal file
@ -0,0 +1,19 @@
|
||||
import matplotlib.pyplot as plt
|
||||
import librosa
|
||||
import numpy as np
|
||||
import os
|
||||
import sys
|
||||
|
||||
args = sys.argv
|
||||
|
||||
file_path = args[1]
|
||||
file_name = os.path.basename(file_path)
|
||||
|
||||
(sig, rate) = librosa.load(file_path, sr=None, mono=True, dtype=np.float32)
|
||||
plt.specgram(sig, Fs=rate, NFFT=2048)
|
||||
|
||||
plt.subplots_adjust(left=0,right=1,bottom=0,top=1)
|
||||
plt.axis('tight')
|
||||
plt.axis('off')
|
||||
|
||||
plt.savefig(f"/var/www/chiro-canto/public/storage/spectrograms/{file_name}.png")
|
46
public/src/spectro_librosa.py
Normal file
46
public/src/spectro_librosa.py
Normal file
@ -0,0 +1,46 @@
|
||||
_wav_file_ = "/var/www/chiro-canto/public/storage/records/PaRecAR628069_20200526_040726.wav"
|
||||
|
||||
def spectogram_librosa(_wav_file_):
|
||||
import librosa
|
||||
import pylab
|
||||
import numpy as np
|
||||
import matplotlib.pyplot as plt
|
||||
|
||||
(sig, rate) = librosa.load(_wav_file_, sr=None, mono=True, dtype=np.float32)
|
||||
plt.specgram(sig, Fs=rate)
|
||||
plt.savefig('spectrogram3.png')
|
||||
|
||||
def graph_spectrogram_wave(wav_file):
|
||||
import wave
|
||||
import pylab
|
||||
import matplotlib.pyplot as plt
|
||||
def get_wav_info(wav_file):
|
||||
wav = wave.open(wav_file, 'r')
|
||||
frames = wav.readframes(-1)
|
||||
sound_info = pylab.fromstring(frames, 'int16')
|
||||
frame_rate = wav.getframerate()
|
||||
wav.close()
|
||||
return sound_info, frame_rate
|
||||
sound_info, frame_rate = get_wav_info(wav_file)
|
||||
# pylab.figure(num=3, figsize=(10, 6))
|
||||
# pylab.title('spectrogram pylab with wav_file')
|
||||
plt.specgram(sound_info, Fs=frame_rate)
|
||||
plt.savefig('spectrogram2.png')
|
||||
|
||||
|
||||
def graph_wavfileread(_wav_file_):
|
||||
import matplotlib.pyplot as plt
|
||||
from scipy import signal
|
||||
from scipy.io import wavfile
|
||||
import numpy as np
|
||||
sample_rate, samples = wavfile.read(_wav_file_)
|
||||
frequencies, times, spectrogram = signal.spectrogram(samples,sample_rate,nfft=1024)
|
||||
plt.pcolormesh(times, frequencies, 10*np.log10(spectrogram))
|
||||
plt.ylabel('Frequency [Hz]')
|
||||
plt.xlabel('Time [sec]')
|
||||
plt.savefig("spectogram1.png")
|
||||
|
||||
|
||||
spectogram_librosa(_wav_file_)
|
||||
#graph_wavfileread(_wav_file_)
|
||||
#graph_spectrogram_wave(_wav_file_)
|
@ -79,7 +79,7 @@ input {
|
||||
}
|
||||
|
||||
/* Style inputs with type="text", select elements and textareas */
|
||||
input[type=text], input[type=email], input[type=url], input[type=password], select, textarea {
|
||||
input[type=text], input[type=email], input[type=url], input[type=password], input[type=number], select, textarea {
|
||||
width: 100%; /* Full width */
|
||||
padding: 12px; /* Some padding */
|
||||
border: 1px solid #ccc; /* Gray border */
|
||||
@ -201,7 +201,7 @@ iframe html body {
|
||||
|
||||
h3, p{
|
||||
padding: 1em;
|
||||
width: 15em;
|
||||
width: auto;
|
||||
}
|
||||
|
||||
p.large {
|
||||
@ -223,6 +223,15 @@ tr:nth-child(even) {
|
||||
background-color: #dddddd;
|
||||
}
|
||||
|
||||
table a {
|
||||
text-decoration: none;
|
||||
color: black;
|
||||
}
|
||||
|
||||
table a:hover {
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
#searchbar {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
|
@ -28,6 +28,9 @@ if (isset($_POST['submit']))
|
||||
if (move_uploaded_file($_FILES['file']['tmp_name'], $target_file))
|
||||
{
|
||||
echo "The file ". htmlspecialchars(basename($_FILES['file']['name']))." has been uploaded.";
|
||||
// Create a spectogram of the file :
|
||||
|
||||
exec("python $root./src/spectro_cli.py ".$_FILES['file']['name']);
|
||||
} else {
|
||||
echo "Sorry, there was an error uploading your file";
|
||||
}
|
||||
|
7
public/vendor/autoload.php
vendored
Normal file
7
public/vendor/autoload.php
vendored
Normal file
@ -0,0 +1,7 @@
|
||||
<?php
|
||||
|
||||
// autoload.php @generated by Composer
|
||||
|
||||
require_once __DIR__ . '/composer/autoload_real.php';
|
||||
|
||||
return ComposerAutoloaderInit2a1773885b3c09785f9319782aba9af7::getLoader();
|
479
public/vendor/composer/ClassLoader.php
vendored
Normal file
479
public/vendor/composer/ClassLoader.php
vendored
Normal file
@ -0,0 +1,479 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of Composer.
|
||||
*
|
||||
* (c) Nils Adermann <naderman@naderman.de>
|
||||
* Jordi Boggiano <j.boggiano@seld.be>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
|
||||
namespace Composer\Autoload;
|
||||
|
||||
/**
|
||||
* ClassLoader implements a PSR-0, PSR-4 and classmap class loader.
|
||||
*
|
||||
* $loader = new \Composer\Autoload\ClassLoader();
|
||||
*
|
||||
* // register classes with namespaces
|
||||
* $loader->add('Symfony\Component', __DIR__.'/component');
|
||||
* $loader->add('Symfony', __DIR__.'/framework');
|
||||
*
|
||||
* // activate the autoloader
|
||||
* $loader->register();
|
||||
*
|
||||
* // to enable searching the include path (eg. for PEAR packages)
|
||||
* $loader->setUseIncludePath(true);
|
||||
*
|
||||
* In this example, if you try to use a class in the Symfony\Component
|
||||
* namespace or one of its children (Symfony\Component\Console for instance),
|
||||
* the autoloader will first look for the class under the component/
|
||||
* directory, and it will then fallback to the framework/ directory if not
|
||||
* found before giving up.
|
||||
*
|
||||
* This class is loosely based on the Symfony UniversalClassLoader.
|
||||
*
|
||||
* @author Fabien Potencier <fabien@symfony.com>
|
||||
* @author Jordi Boggiano <j.boggiano@seld.be>
|
||||
* @see https://www.php-fig.org/psr/psr-0/
|
||||
* @see https://www.php-fig.org/psr/psr-4/
|
||||
*/
|
||||
class ClassLoader
|
||||
{
|
||||
private $vendorDir;
|
||||
|
||||
// PSR-4
|
||||
private $prefixLengthsPsr4 = array();
|
||||
private $prefixDirsPsr4 = array();
|
||||
private $fallbackDirsPsr4 = array();
|
||||
|
||||
// PSR-0
|
||||
private $prefixesPsr0 = array();
|
||||
private $fallbackDirsPsr0 = array();
|
||||
|
||||
private $useIncludePath = false;
|
||||
private $classMap = array();
|
||||
private $classMapAuthoritative = false;
|
||||
private $missingClasses = array();
|
||||
private $apcuPrefix;
|
||||
|
||||
private static $registeredLoaders = array();
|
||||
|
||||
public function __construct($vendorDir = null)
|
||||
{
|
||||
$this->vendorDir = $vendorDir;
|
||||
}
|
||||
|
||||
public function getPrefixes()
|
||||
{
|
||||
if (!empty($this->prefixesPsr0)) {
|
||||
return call_user_func_array('array_merge', array_values($this->prefixesPsr0));
|
||||
}
|
||||
|
||||
return array();
|
||||
}
|
||||
|
||||
public function getPrefixesPsr4()
|
||||
{
|
||||
return $this->prefixDirsPsr4;
|
||||
}
|
||||
|
||||
public function getFallbackDirs()
|
||||
{
|
||||
return $this->fallbackDirsPsr0;
|
||||
}
|
||||
|
||||
public function getFallbackDirsPsr4()
|
||||
{
|
||||
return $this->fallbackDirsPsr4;
|
||||
}
|
||||
|
||||
public function getClassMap()
|
||||
{
|
||||
return $this->classMap;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param array $classMap Class to filename map
|
||||
*/
|
||||
public function addClassMap(array $classMap)
|
||||
{
|
||||
if ($this->classMap) {
|
||||
$this->classMap = array_merge($this->classMap, $classMap);
|
||||
} else {
|
||||
$this->classMap = $classMap;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers a set of PSR-0 directories for a given prefix, either
|
||||
* appending or prepending to the ones previously set for this prefix.
|
||||
*
|
||||
* @param string $prefix The prefix
|
||||
* @param array|string $paths The PSR-0 root directories
|
||||
* @param bool $prepend Whether to prepend the directories
|
||||
*/
|
||||
public function add($prefix, $paths, $prepend = false)
|
||||
{
|
||||
if (!$prefix) {
|
||||
if ($prepend) {
|
||||
$this->fallbackDirsPsr0 = array_merge(
|
||||
(array) $paths,
|
||||
$this->fallbackDirsPsr0
|
||||
);
|
||||
} else {
|
||||
$this->fallbackDirsPsr0 = array_merge(
|
||||
$this->fallbackDirsPsr0,
|
||||
(array) $paths
|
||||
);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
$first = $prefix[0];
|
||||
if (!isset($this->prefixesPsr0[$first][$prefix])) {
|
||||
$this->prefixesPsr0[$first][$prefix] = (array) $paths;
|
||||
|
||||
return;
|
||||
}
|
||||
if ($prepend) {
|
||||
$this->prefixesPsr0[$first][$prefix] = array_merge(
|
||||
(array) $paths,
|
||||
$this->prefixesPsr0[$first][$prefix]
|
||||
);
|
||||
} else {
|
||||
$this->prefixesPsr0[$first][$prefix] = array_merge(
|
||||
$this->prefixesPsr0[$first][$prefix],
|
||||
(array) $paths
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers a set of PSR-4 directories for a given namespace, either
|
||||
* appending or prepending to the ones previously set for this namespace.
|
||||
*
|
||||
* @param string $prefix The prefix/namespace, with trailing '\\'
|
||||
* @param array|string $paths The PSR-4 base directories
|
||||
* @param bool $prepend Whether to prepend the directories
|
||||
*
|
||||
* @throws \InvalidArgumentException
|
||||
*/
|
||||
public function addPsr4($prefix, $paths, $prepend = false)
|
||||
{
|
||||
if (!$prefix) {
|
||||
// Register directories for the root namespace.
|
||||
if ($prepend) {
|
||||
$this->fallbackDirsPsr4 = array_merge(
|
||||
(array) $paths,
|
||||
$this->fallbackDirsPsr4
|
||||
);
|
||||
} else {
|
||||
$this->fallbackDirsPsr4 = array_merge(
|
||||
$this->fallbackDirsPsr4,
|
||||
(array) $paths
|
||||
);
|
||||
}
|
||||
} elseif (!isset($this->prefixDirsPsr4[$prefix])) {
|
||||
// Register directories for a new namespace.
|
||||
$length = strlen($prefix);
|
||||
if ('\\' !== $prefix[$length - 1]) {
|
||||
throw new \InvalidArgumentException("A non-empty PSR-4 prefix must end with a namespace separator.");
|
||||
}
|
||||
$this->prefixLengthsPsr4[$prefix[0]][$prefix] = $length;
|
||||
$this->prefixDirsPsr4[$prefix] = (array) $paths;
|
||||
} elseif ($prepend) {
|
||||
// Prepend directories for an already registered namespace.
|
||||
$this->prefixDirsPsr4[$prefix] = array_merge(
|
||||
(array) $paths,
|
||||
$this->prefixDirsPsr4[$prefix]
|
||||
);
|
||||
} else {
|
||||
// Append directories for an already registered namespace.
|
||||
$this->prefixDirsPsr4[$prefix] = array_merge(
|
||||
$this->prefixDirsPsr4[$prefix],
|
||||
(array) $paths
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers a set of PSR-0 directories for a given prefix,
|
||||
* replacing any others previously set for this prefix.
|
||||
*
|
||||
* @param string $prefix The prefix
|
||||
* @param array|string $paths The PSR-0 base directories
|
||||
*/
|
||||
public function set($prefix, $paths)
|
||||
{
|
||||
if (!$prefix) {
|
||||
$this->fallbackDirsPsr0 = (array) $paths;
|
||||
} else {
|
||||
$this->prefixesPsr0[$prefix[0]][$prefix] = (array) $paths;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers a set of PSR-4 directories for a given namespace,
|
||||
* replacing any others previously set for this namespace.
|
||||
*
|
||||
* @param string $prefix The prefix/namespace, with trailing '\\'
|
||||
* @param array|string $paths The PSR-4 base directories
|
||||
*
|
||||
* @throws \InvalidArgumentException
|
||||
*/
|
||||
public function setPsr4($prefix, $paths)
|
||||
{
|
||||
if (!$prefix) {
|
||||
$this->fallbackDirsPsr4 = (array) $paths;
|
||||
} else {
|
||||
$length = strlen($prefix);
|
||||
if ('\\' !== $prefix[$length - 1]) {
|
||||
throw new \InvalidArgumentException("A non-empty PSR-4 prefix must end with a namespace separator.");
|
||||
}
|
||||
$this->prefixLengthsPsr4[$prefix[0]][$prefix] = $length;
|
||||
$this->prefixDirsPsr4[$prefix] = (array) $paths;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Turns on searching the include path for class files.
|
||||
*
|
||||
* @param bool $useIncludePath
|
||||
*/
|
||||
public function setUseIncludePath($useIncludePath)
|
||||
{
|
||||
$this->useIncludePath = $useIncludePath;
|
||||
}
|
||||
|
||||
/**
|
||||
* Can be used to check if the autoloader uses the include path to check
|
||||
* for classes.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function getUseIncludePath()
|
||||
{
|
||||
return $this->useIncludePath;
|
||||
}
|
||||
|
||||
/**
|
||||
* Turns off searching the prefix and fallback directories for classes
|
||||
* that have not been registered with the class map.
|
||||
*
|
||||
* @param bool $classMapAuthoritative
|
||||
*/
|
||||
public function setClassMapAuthoritative($classMapAuthoritative)
|
||||
{
|
||||
$this->classMapAuthoritative = $classMapAuthoritative;
|
||||
}
|
||||
|
||||
/**
|
||||
* Should class lookup fail if not found in the current class map?
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function isClassMapAuthoritative()
|
||||
{
|
||||
return $this->classMapAuthoritative;
|
||||
}
|
||||
|
||||
/**
|
||||
* APCu prefix to use to cache found/not-found classes, if the extension is enabled.
|
||||
*
|
||||
* @param string|null $apcuPrefix
|
||||
*/
|
||||
public function setApcuPrefix($apcuPrefix)
|
||||
{
|
||||
$this->apcuPrefix = function_exists('apcu_fetch') && filter_var(ini_get('apc.enabled'), FILTER_VALIDATE_BOOLEAN) ? $apcuPrefix : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* The APCu prefix in use, or null if APCu caching is not enabled.
|
||||
*
|
||||
* @return string|null
|
||||
*/
|
||||
public function getApcuPrefix()
|
||||
{
|
||||
return $this->apcuPrefix;
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers this instance as an autoloader.
|
||||
*
|
||||
* @param bool $prepend Whether to prepend the autoloader or not
|
||||
*/
|
||||
public function register($prepend = false)
|
||||
{
|
||||
spl_autoload_register(array($this, 'loadClass'), true, $prepend);
|
||||
|
||||
if (null === $this->vendorDir) {
|
||||
return;
|
||||
}
|
||||
|
||||
if ($prepend) {
|
||||
self::$registeredLoaders = array($this->vendorDir => $this) + self::$registeredLoaders;
|
||||
} else {
|
||||
unset(self::$registeredLoaders[$this->vendorDir]);
|
||||
self::$registeredLoaders[$this->vendorDir] = $this;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Unregisters this instance as an autoloader.
|
||||
*/
|
||||
public function unregister()
|
||||
{
|
||||
spl_autoload_unregister(array($this, 'loadClass'));
|
||||
|
||||
if (null !== $this->vendorDir) {
|
||||
unset(self::$registeredLoaders[$this->vendorDir]);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Loads the given class or interface.
|
||||
*
|
||||
* @param string $class The name of the class
|
||||
* @return bool|null True if loaded, null otherwise
|
||||
*/
|
||||
public function loadClass($class)
|
||||
{
|
||||
if ($file = $this->findFile($class)) {
|
||||
includeFile($file);
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Finds the path to the file where the class is defined.
|
||||
*
|
||||
* @param string $class The name of the class
|
||||
*
|
||||
* @return string|false The path if found, false otherwise
|
||||
*/
|
||||
public function findFile($class)
|
||||
{
|
||||
// class map lookup
|
||||
if (isset($this->classMap[$class])) {
|
||||
return $this->classMap[$class];
|
||||
}
|
||||
if ($this->classMapAuthoritative || isset($this->missingClasses[$class])) {
|
||||
return false;
|
||||
}
|
||||
if (null !== $this->apcuPrefix) {
|
||||
$file = apcu_fetch($this->apcuPrefix.$class, $hit);
|
||||
if ($hit) {
|
||||
return $file;
|
||||
}
|
||||
}
|
||||
|
||||
$file = $this->findFileWithExtension($class, '.php');
|
||||
|
||||
// Search for Hack files if we are running on HHVM
|
||||
if (false === $file && defined('HHVM_VERSION')) {
|
||||
$file = $this->findFileWithExtension($class, '.hh');
|
||||
}
|
||||
|
||||
if (null !== $this->apcuPrefix) {
|
||||
apcu_add($this->apcuPrefix.$class, $file);
|
||||
}
|
||||
|
||||
if (false === $file) {
|
||||
// Remember that this class does not exist.
|
||||
$this->missingClasses[$class] = true;
|
||||
}
|
||||
|
||||
return $file;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the currently registered loaders indexed by their corresponding vendor directories.
|
||||
*
|
||||
* @return self[]
|
||||
*/
|
||||
public static function getRegisteredLoaders()
|
||||
{
|
||||
return self::$registeredLoaders;
|
||||
}
|
||||
|
||||
private function findFileWithExtension($class, $ext)
|
||||
{
|
||||
// PSR-4 lookup
|
||||
$logicalPathPsr4 = strtr($class, '\\', DIRECTORY_SEPARATOR) . $ext;
|
||||
|
||||
$first = $class[0];
|
||||
if (isset($this->prefixLengthsPsr4[$first])) {
|
||||
$subPath = $class;
|
||||
while (false !== $lastPos = strrpos($subPath, '\\')) {
|
||||
$subPath = substr($subPath, 0, $lastPos);
|
||||
$search = $subPath . '\\';
|
||||
if (isset($this->prefixDirsPsr4[$search])) {
|
||||
$pathEnd = DIRECTORY_SEPARATOR . substr($logicalPathPsr4, $lastPos + 1);
|
||||
foreach ($this->prefixDirsPsr4[$search] as $dir) {
|
||||
if (file_exists($file = $dir . $pathEnd)) {
|
||||
return $file;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// PSR-4 fallback dirs
|
||||
foreach ($this->fallbackDirsPsr4 as $dir) {
|
||||
if (file_exists($file = $dir . DIRECTORY_SEPARATOR . $logicalPathPsr4)) {
|
||||
return $file;
|
||||
}
|
||||
}
|
||||
|
||||
// PSR-0 lookup
|
||||
if (false !== $pos = strrpos($class, '\\')) {
|
||||
// namespaced class name
|
||||
$logicalPathPsr0 = substr($logicalPathPsr4, 0, $pos + 1)
|
||||
. strtr(substr($logicalPathPsr4, $pos + 1), '_', DIRECTORY_SEPARATOR);
|
||||
} else {
|
||||
// PEAR-like class name
|
||||
$logicalPathPsr0 = strtr($class, '_', DIRECTORY_SEPARATOR) . $ext;
|
||||
}
|
||||
|
||||
if (isset($this->prefixesPsr0[$first])) {
|
||||
foreach ($this->prefixesPsr0[$first] as $prefix => $dirs) {
|
||||
if (0 === strpos($class, $prefix)) {
|
||||
foreach ($dirs as $dir) {
|
||||
if (file_exists($file = $dir . DIRECTORY_SEPARATOR . $logicalPathPsr0)) {
|
||||
return $file;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// PSR-0 fallback dirs
|
||||
foreach ($this->fallbackDirsPsr0 as $dir) {
|
||||
if (file_exists($file = $dir . DIRECTORY_SEPARATOR . $logicalPathPsr0)) {
|
||||
return $file;
|
||||
}
|
||||
}
|
||||
|
||||
// PSR-0 include paths.
|
||||
if ($this->useIncludePath && $file = stream_resolve_include_path($logicalPathPsr0)) {
|
||||
return $file;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Scope isolated include.
|
||||
*
|
||||
* Prevents access to $this/self from included files.
|
||||
*/
|
||||
function includeFile($file)
|
||||
{
|
||||
include $file;
|
||||
}
|
292
public/vendor/composer/InstalledVersions.php
vendored
Normal file
292
public/vendor/composer/InstalledVersions.php
vendored
Normal file
@ -0,0 +1,292 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of Composer.
|
||||
*
|
||||
* (c) Nils Adermann <naderman@naderman.de>
|
||||
* Jordi Boggiano <j.boggiano@seld.be>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
|
||||
namespace Composer;
|
||||
|
||||
use Composer\Autoload\ClassLoader;
|
||||
use Composer\Semver\VersionParser;
|
||||
|
||||
/**
|
||||
* This class is copied in every Composer installed project and available to all
|
||||
*
|
||||
* To require it's presence, you can require `composer-runtime-api ^2.0`
|
||||
*/
|
||||
class InstalledVersions
|
||||
{
|
||||
private static $installed = array (
|
||||
'root' =>
|
||||
array (
|
||||
'pretty_version' => 'dev-main',
|
||||
'version' => 'dev-main',
|
||||
'aliases' =>
|
||||
array (
|
||||
),
|
||||
'reference' => '8192e30810af84d5b9cb756af8834e31842d5bf8',
|
||||
'name' => '__root__',
|
||||
),
|
||||
'versions' =>
|
||||
array (
|
||||
'__root__' =>
|
||||
array (
|
||||
'pretty_version' => 'dev-main',
|
||||
'version' => 'dev-main',
|
||||
'aliases' =>
|
||||
array (
|
||||
),
|
||||
'reference' => '8192e30810af84d5b9cb756af8834e31842d5bf8',
|
||||
),
|
||||
'erusev/parsedown' =>
|
||||
array (
|
||||
'pretty_version' => '1.7.4',
|
||||
'version' => '1.7.4.0',
|
||||
'aliases' =>
|
||||
array (
|
||||
),
|
||||
'reference' => 'cb17b6477dfff935958ba01325f2e8a2bfa6dab3',
|
||||
),
|
||||
),
|
||||
);
|
||||
private static $canGetVendors;
|
||||
private static $installedByVendor = array();
|
||||
|
||||
/**
|
||||
* Returns a list of all package names which are present, either by being installed, replaced or provided
|
||||
*
|
||||
* @return string[]
|
||||
* @psalm-return list<string>
|
||||
*/
|
||||
public static function getInstalledPackages()
|
||||
{
|
||||
$packages = array();
|
||||
foreach (self::getInstalled() as $installed) {
|
||||
$packages[] = array_keys($installed['versions']);
|
||||
}
|
||||
|
||||
|
||||
if (1 === \count($packages)) {
|
||||
return $packages[0];
|
||||
}
|
||||
|
||||
return array_keys(array_flip(\call_user_func_array('array_merge', $packages)));
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks whether the given package is installed
|
||||
*
|
||||
* This also returns true if the package name is provided or replaced by another package
|
||||
*
|
||||
* @param string $packageName
|
||||
* @return bool
|
||||
*/
|
||||
public static function isInstalled($packageName)
|
||||
{
|
||||
foreach (self::getInstalled() as $installed) {
|
||||
if (isset($installed['versions'][$packageName])) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks whether the given package satisfies a version constraint
|
||||
*
|
||||
* e.g. If you want to know whether version 2.3+ of package foo/bar is installed, you would call:
|
||||
*
|
||||
* Composer\InstalledVersions::satisfies(new VersionParser, 'foo/bar', '^2.3')
|
||||
*
|
||||
* @param VersionParser $parser Install composer/semver to have access to this class and functionality
|
||||
* @param string $packageName
|
||||
* @param string|null $constraint A version constraint to check for, if you pass one you have to make sure composer/semver is required by your package
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public static function satisfies(VersionParser $parser, $packageName, $constraint)
|
||||
{
|
||||
$constraint = $parser->parseConstraints($constraint);
|
||||
$provided = $parser->parseConstraints(self::getVersionRanges($packageName));
|
||||
|
||||
return $provided->matches($constraint);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a version constraint representing all the range(s) which are installed for a given package
|
||||
*
|
||||
* It is easier to use this via isInstalled() with the $constraint argument if you need to check
|
||||
* whether a given version of a package is installed, and not just whether it exists
|
||||
*
|
||||
* @param string $packageName
|
||||
* @return string Version constraint usable with composer/semver
|
||||
*/
|
||||
public static function getVersionRanges($packageName)
|
||||
{
|
||||
foreach (self::getInstalled() as $installed) {
|
||||
if (!isset($installed['versions'][$packageName])) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$ranges = array();
|
||||
if (isset($installed['versions'][$packageName]['pretty_version'])) {
|
||||
$ranges[] = $installed['versions'][$packageName]['pretty_version'];
|
||||
}
|
||||
if (array_key_exists('aliases', $installed['versions'][$packageName])) {
|
||||
$ranges = array_merge($ranges, $installed['versions'][$packageName]['aliases']);
|
||||
}
|
||||
if (array_key_exists('replaced', $installed['versions'][$packageName])) {
|
||||
$ranges = array_merge($ranges, $installed['versions'][$packageName]['replaced']);
|
||||
}
|
||||
if (array_key_exists('provided', $installed['versions'][$packageName])) {
|
||||
$ranges = array_merge($ranges, $installed['versions'][$packageName]['provided']);
|
||||
}
|
||||
|
||||
return implode(' || ', $ranges);
|
||||
}
|
||||
|
||||
throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
|
||||
}
|
||||
|
||||
/**
|
||||
* @param string $packageName
|
||||
* @return string|null If the package is being replaced or provided but is not really installed, null will be returned as version, use satisfies or getVersionRanges if you need to know if a given version is present
|
||||
*/
|
||||
public static function getVersion($packageName)
|
||||
{
|
||||
foreach (self::getInstalled() as $installed) {
|
||||
if (!isset($installed['versions'][$packageName])) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!isset($installed['versions'][$packageName]['version'])) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return $installed['versions'][$packageName]['version'];
|
||||
}
|
||||
|
||||
throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
|
||||
}
|
||||
|
||||
/**
|
||||
* @param string $packageName
|
||||
* @return string|null If the package is being replaced or provided but is not really installed, null will be returned as version, use satisfies or getVersionRanges if you need to know if a given version is present
|
||||
*/
|
||||
public static function getPrettyVersion($packageName)
|
||||
{
|
||||
foreach (self::getInstalled() as $installed) {
|
||||
if (!isset($installed['versions'][$packageName])) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!isset($installed['versions'][$packageName]['pretty_version'])) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return $installed['versions'][$packageName]['pretty_version'];
|
||||
}
|
||||
|
||||
throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
|
||||
}
|
||||
|
||||
/**
|
||||
* @param string $packageName
|
||||
* @return string|null If the package is being replaced or provided but is not really installed, null will be returned as reference
|
||||
*/
|
||||
public static function getReference($packageName)
|
||||
{
|
||||
foreach (self::getInstalled() as $installed) {
|
||||
if (!isset($installed['versions'][$packageName])) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!isset($installed['versions'][$packageName]['reference'])) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return $installed['versions'][$packageName]['reference'];
|
||||
}
|
||||
|
||||
throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
|
||||
}
|
||||
|
||||
/**
|
||||
* @return array
|
||||
* @psalm-return array{name: string, version: string, reference: string, pretty_version: string, aliases: string[]}
|
||||
*/
|
||||
public static function getRootPackage()
|
||||
{
|
||||
$installed = self::getInstalled();
|
||||
|
||||
return $installed[0]['root'];
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the raw installed.php data for custom implementations
|
||||
*
|
||||
* @return array[]
|
||||
* @psalm-return array{root: array{name: string, version: string, reference: string, pretty_version: string, aliases: string[]}, versions: list<string, array{pretty_version: ?string, version: ?string, aliases: ?string[], reference: ?string, replaced: ?string[], provided: ?string[]}>}
|
||||
*/
|
||||
public static function getRawData()
|
||||
{
|
||||
return self::$installed;
|
||||
}
|
||||
|
||||
/**
|
||||
* Lets you reload the static array from another file
|
||||
*
|
||||
* This is only useful for complex integrations in which a project needs to use
|
||||
* this class but then also needs to execute another project's autoloader in process,
|
||||
* and wants to ensure both projects have access to their version of installed.php.
|
||||
*
|
||||
* A typical case would be PHPUnit, where it would need to make sure it reads all
|
||||
* the data it needs from this class, then call reload() with
|
||||
* `require $CWD/vendor/composer/installed.php` (or similar) as input to make sure
|
||||
* the project in which it runs can then also use this class safely, without
|
||||
* interference between PHPUnit's dependencies and the project's dependencies.
|
||||
*
|
||||
* @param array[] $data A vendor/composer/installed.php data set
|
||||
* @return void
|
||||
*
|
||||
* @psalm-param array{root: array{name: string, version: string, reference: string, pretty_version: string, aliases: string[]}, versions: list<string, array{pretty_version: ?string, version: ?string, aliases: ?string[], reference: ?string, replaced: ?string[], provided: ?string[]}>} $data
|
||||
*/
|
||||
public static function reload($data)
|
||||
{
|
||||
self::$installed = $data;
|
||||
self::$installedByVendor = array();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return array[]
|
||||
*/
|
||||
private static function getInstalled()
|
||||
{
|
||||
if (null === self::$canGetVendors) {
|
||||
self::$canGetVendors = method_exists('Composer\Autoload\ClassLoader', 'getRegisteredLoaders');
|
||||
}
|
||||
|
||||
$installed = array();
|
||||
|
||||
if (self::$canGetVendors) {
|
||||
foreach (ClassLoader::getRegisteredLoaders() as $vendorDir => $loader) {
|
||||
if (isset(self::$installedByVendor[$vendorDir])) {
|
||||
$installed[] = self::$installedByVendor[$vendorDir];
|
||||
} elseif (is_file($vendorDir.'/composer/installed.php')) {
|
||||
$installed[] = self::$installedByVendor[$vendorDir] = require $vendorDir.'/composer/installed.php';
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$installed[] = self::$installed;
|
||||
|
||||
return $installed;
|
||||
}
|
||||
}
|
19
public/vendor/composer/LICENSE
vendored
Normal file
19
public/vendor/composer/LICENSE
vendored
Normal file
@ -0,0 +1,19 @@
|
||||
Copyright (c) Nils Adermann, Jordi Boggiano
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is furnished
|
||||
to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
10
public/vendor/composer/autoload_classmap.php
vendored
Normal file
10
public/vendor/composer/autoload_classmap.php
vendored
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
// autoload_classmap.php @generated by Composer
|
||||
|
||||
$vendorDir = dirname(dirname(__FILE__));
|
||||
$baseDir = dirname($vendorDir);
|
||||
|
||||
return array(
|
||||
'Composer\\InstalledVersions' => $vendorDir . '/composer/InstalledVersions.php',
|
||||
);
|
10
public/vendor/composer/autoload_namespaces.php
vendored
Normal file
10
public/vendor/composer/autoload_namespaces.php
vendored
Normal file
@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
// autoload_namespaces.php @generated by Composer
|
||||
|
||||
$vendorDir = dirname(dirname(__FILE__));
|
||||
$baseDir = dirname($vendorDir);
|
||||
|
||||
return array(
|
||||
'Parsedown' => array($vendorDir . '/erusev/parsedown'),
|
||||
);
|
9
public/vendor/composer/autoload_psr4.php
vendored
Normal file
9
public/vendor/composer/autoload_psr4.php
vendored
Normal file
@ -0,0 +1,9 @@
|
||||
<?php
|
||||
|
||||
// autoload_psr4.php @generated by Composer
|
||||
|
||||
$vendorDir = dirname(dirname(__FILE__));
|
||||
$baseDir = dirname($vendorDir);
|
||||
|
||||
return array(
|
||||
);
|
57
public/vendor/composer/autoload_real.php
vendored
Normal file
57
public/vendor/composer/autoload_real.php
vendored
Normal file
@ -0,0 +1,57 @@
|
||||
<?php
|
||||
|
||||
// autoload_real.php @generated by Composer
|
||||
|
||||
class ComposerAutoloaderInit2a1773885b3c09785f9319782aba9af7
|
||||
{
|
||||
private static $loader;
|
||||
|
||||
public static function loadClassLoader($class)
|
||||
{
|
||||
if ('Composer\Autoload\ClassLoader' === $class) {
|
||||
require __DIR__ . '/ClassLoader.php';
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return \Composer\Autoload\ClassLoader
|
||||
*/
|
||||
public static function getLoader()
|
||||
{
|
||||
if (null !== self::$loader) {
|
||||
return self::$loader;
|
||||
}
|
||||
|
||||
require __DIR__ . '/platform_check.php';
|
||||
|
||||
spl_autoload_register(array('ComposerAutoloaderInit2a1773885b3c09785f9319782aba9af7', 'loadClassLoader'), true, true);
|
||||
self::$loader = $loader = new \Composer\Autoload\ClassLoader(\dirname(\dirname(__FILE__)));
|
||||
spl_autoload_unregister(array('ComposerAutoloaderInit2a1773885b3c09785f9319782aba9af7', 'loadClassLoader'));
|
||||
|
||||
$useStaticLoader = PHP_VERSION_ID >= 50600 && !defined('HHVM_VERSION') && (!function_exists('zend_loader_file_encoded') || !zend_loader_file_encoded());
|
||||
if ($useStaticLoader) {
|
||||
require __DIR__ . '/autoload_static.php';
|
||||
|
||||
call_user_func(\Composer\Autoload\ComposerStaticInit2a1773885b3c09785f9319782aba9af7::getInitializer($loader));
|
||||
} else {
|
||||
$map = require __DIR__ . '/autoload_namespaces.php';
|
||||
foreach ($map as $namespace => $path) {
|
||||
$loader->set($namespace, $path);
|
||||
}
|
||||
|
||||
$map = require __DIR__ . '/autoload_psr4.php';
|
||||
foreach ($map as $namespace => $path) {
|
||||
$loader->setPsr4($namespace, $path);
|
||||
}
|
||||
|
||||
$classMap = require __DIR__ . '/autoload_classmap.php';
|
||||
if ($classMap) {
|
||||
$loader->addClassMap($classMap);
|
||||
}
|
||||
}
|
||||
|
||||
$loader->register(true);
|
||||
|
||||
return $loader;
|
||||
}
|
||||
}
|
31
public/vendor/composer/autoload_static.php
vendored
Normal file
31
public/vendor/composer/autoload_static.php
vendored
Normal file
@ -0,0 +1,31 @@
|
||||
<?php
|
||||
|
||||
// autoload_static.php @generated by Composer
|
||||
|
||||
namespace Composer\Autoload;
|
||||
|
||||
class ComposerStaticInit2a1773885b3c09785f9319782aba9af7
|
||||
{
|
||||
public static $prefixesPsr0 = array (
|
||||
'P' =>
|
||||
array (
|
||||
'Parsedown' =>
|
||||
array (
|
||||
0 => __DIR__ . '/..' . '/erusev/parsedown',
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
public static $classMap = array (
|
||||
'Composer\\InstalledVersions' => __DIR__ . '/..' . '/composer/InstalledVersions.php',
|
||||
);
|
||||
|
||||
public static function getInitializer(ClassLoader $loader)
|
||||
{
|
||||
return \Closure::bind(function () use ($loader) {
|
||||
$loader->prefixesPsr0 = ComposerStaticInit2a1773885b3c09785f9319782aba9af7::$prefixesPsr0;
|
||||
$loader->classMap = ComposerStaticInit2a1773885b3c09785f9319782aba9af7::$classMap;
|
||||
|
||||
}, null, ClassLoader::class);
|
||||
}
|
||||
}
|
59
public/vendor/composer/installed.json
vendored
Normal file
59
public/vendor/composer/installed.json
vendored
Normal file
@ -0,0 +1,59 @@
|
||||
{
|
||||
"packages": [
|
||||
{
|
||||
"name": "erusev/parsedown",
|
||||
"version": "1.7.4",
|
||||
"version_normalized": "1.7.4.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/erusev/parsedown.git",
|
||||
"reference": "cb17b6477dfff935958ba01325f2e8a2bfa6dab3"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/erusev/parsedown/zipball/cb17b6477dfff935958ba01325f2e8a2bfa6dab3",
|
||||
"reference": "cb17b6477dfff935958ba01325f2e8a2bfa6dab3",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"ext-mbstring": "*",
|
||||
"php": ">=5.3.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "^4.8.35"
|
||||
},
|
||||
"time": "2019-12-30T22:54:17+00:00",
|
||||
"type": "library",
|
||||
"installation-source": "dist",
|
||||
"autoload": {
|
||||
"psr-0": {
|
||||
"Parsedown": ""
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Emanuil Rusev",
|
||||
"email": "hello@erusev.com",
|
||||
"homepage": "http://erusev.com"
|
||||
}
|
||||
],
|
||||
"description": "Parser for Markdown.",
|
||||
"homepage": "http://parsedown.org",
|
||||
"keywords": [
|
||||
"markdown",
|
||||
"parser"
|
||||
],
|
||||
"support": {
|
||||
"issues": "https://github.com/erusev/parsedown/issues",
|
||||
"source": "https://github.com/erusev/parsedown/tree/1.7.x"
|
||||
},
|
||||
"install-path": "../erusev/parsedown"
|
||||
}
|
||||
],
|
||||
"dev": true,
|
||||
"dev-package-names": []
|
||||
}
|
33
public/vendor/composer/installed.php
vendored
Normal file
33
public/vendor/composer/installed.php
vendored
Normal file
@ -0,0 +1,33 @@
|
||||
<?php return array (
|
||||
'root' =>
|
||||
array (
|
||||
'pretty_version' => 'dev-main',
|
||||
'version' => 'dev-main',
|
||||
'aliases' =>
|
||||
array (
|
||||
),
|
||||
'reference' => '8192e30810af84d5b9cb756af8834e31842d5bf8',
|
||||
'name' => '__root__',
|
||||
),
|
||||
'versions' =>
|
||||
array (
|
||||
'__root__' =>
|
||||
array (
|
||||
'pretty_version' => 'dev-main',
|
||||
'version' => 'dev-main',
|
||||
'aliases' =>
|
||||
array (
|
||||
),
|
||||
'reference' => '8192e30810af84d5b9cb756af8834e31842d5bf8',
|
||||
),
|
||||
'erusev/parsedown' =>
|
||||
array (
|
||||
'pretty_version' => '1.7.4',
|
||||
'version' => '1.7.4.0',
|
||||
'aliases' =>
|
||||
array (
|
||||
),
|
||||
'reference' => 'cb17b6477dfff935958ba01325f2e8a2bfa6dab3',
|
||||
),
|
||||
),
|
||||
);
|
26
public/vendor/composer/platform_check.php
vendored
Normal file
26
public/vendor/composer/platform_check.php
vendored
Normal file
@ -0,0 +1,26 @@
|
||||
<?php
|
||||
|
||||
// platform_check.php @generated by Composer
|
||||
|
||||
$issues = array();
|
||||
|
||||
if (!(PHP_VERSION_ID >= 50300)) {
|
||||
$issues[] = 'Your Composer dependencies require a PHP version ">= 5.3.0". You are running ' . PHP_VERSION . '.';
|
||||
}
|
||||
|
||||
if ($issues) {
|
||||
if (!headers_sent()) {
|
||||
header('HTTP/1.1 500 Internal Server Error');
|
||||
}
|
||||
if (!ini_get('display_errors')) {
|
||||
if (PHP_SAPI === 'cli' || PHP_SAPI === 'phpdbg') {
|
||||
fwrite(STDERR, 'Composer detected issues in your platform:' . PHP_EOL.PHP_EOL . implode(PHP_EOL, $issues) . PHP_EOL.PHP_EOL);
|
||||
} elseif (!headers_sent()) {
|
||||
echo 'Composer detected issues in your platform:' . PHP_EOL.PHP_EOL . str_replace('You are running '.PHP_VERSION.'.', '', implode(PHP_EOL, $issues)) . PHP_EOL.PHP_EOL;
|
||||
}
|
||||
}
|
||||
trigger_error(
|
||||
'Composer detected issues in your platform: ' . implode(' ', $issues),
|
||||
E_USER_ERROR
|
||||
);
|
||||
}
|
20
public/vendor/erusev/parsedown/LICENSE.txt
vendored
Normal file
20
public/vendor/erusev/parsedown/LICENSE.txt
vendored
Normal file
@ -0,0 +1,20 @@
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2013-2018 Emanuil Rusev, erusev.com
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
this software and associated documentation files (the "Software"), to deal in
|
||||
the Software without restriction, including without limitation the rights to
|
||||
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
||||
the Software, and to permit persons to whom the Software is furnished to do so,
|
||||
subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
||||
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
||||
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
|
||||
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
||||
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
1712
public/vendor/erusev/parsedown/Parsedown.php
vendored
Normal file
1712
public/vendor/erusev/parsedown/Parsedown.php
vendored
Normal file
File diff suppressed because it is too large
Load Diff
86
public/vendor/erusev/parsedown/README.md
vendored
Normal file
86
public/vendor/erusev/parsedown/README.md
vendored
Normal file
@ -0,0 +1,86 @@
|
||||
> I also make [Caret](https://caret.io?ref=parsedown) - a Markdown editor for Mac and PC.
|
||||
|
||||
## Parsedown
|
||||
|
||||
[![Build Status](https://img.shields.io/travis/erusev/parsedown/master.svg?style=flat-square)](https://travis-ci.org/erusev/parsedown)
|
||||
<!--[![Total Downloads](http://img.shields.io/packagist/dt/erusev/parsedown.svg?style=flat-square)](https://packagist.org/packages/erusev/parsedown)-->
|
||||
|
||||
Better Markdown Parser in PHP
|
||||
|
||||
[Demo](http://parsedown.org/demo) |
|
||||
[Benchmarks](http://parsedown.org/speed) |
|
||||
[Tests](http://parsedown.org/tests/) |
|
||||
[Documentation](https://github.com/erusev/parsedown/wiki/)
|
||||
|
||||
### Features
|
||||
|
||||
* One File
|
||||
* No Dependencies
|
||||
* Super Fast
|
||||
* Extensible
|
||||
* [GitHub flavored](https://help.github.com/articles/github-flavored-markdown)
|
||||
* Tested in 5.3 to 7.1 and in HHVM
|
||||
* [Markdown Extra extension](https://github.com/erusev/parsedown-extra)
|
||||
|
||||
### Installation
|
||||
|
||||
Include `Parsedown.php` or install [the composer package](https://packagist.org/packages/erusev/parsedown).
|
||||
|
||||
### Example
|
||||
|
||||
``` php
|
||||
$Parsedown = new Parsedown();
|
||||
|
||||
echo $Parsedown->text('Hello _Parsedown_!'); # prints: <p>Hello <em>Parsedown</em>!</p>
|
||||
```
|
||||
|
||||
More examples in [the wiki](https://github.com/erusev/parsedown/wiki/) and in [this video tutorial](http://youtu.be/wYZBY8DEikI).
|
||||
|
||||
### Security
|
||||
|
||||
Parsedown is capable of escaping user-input within the HTML that it generates. Additionally Parsedown will apply sanitisation to additional scripting vectors (such as scripting link destinations) that are introduced by the markdown syntax itself.
|
||||
|
||||
To tell Parsedown that it is processing untrusted user-input, use the following:
|
||||
```php
|
||||
$parsedown = new Parsedown;
|
||||
$parsedown->setSafeMode(true);
|
||||
```
|
||||
|
||||
If instead, you wish to allow HTML within untrusted user-input, but still want output to be free from XSS it is recommended that you make use of a HTML sanitiser that allows HTML tags to be whitelisted, like [HTML Purifier](http://htmlpurifier.org/).
|
||||
|
||||
In both cases you should strongly consider employing defence-in-depth measures, like [deploying a Content-Security-Policy](https://scotthelme.co.uk/content-security-policy-an-introduction/) (a browser security feature) so that your page is likely to be safe even if an attacker finds a vulnerability in one of the first lines of defence above.
|
||||
|
||||
#### Security of Parsedown Extensions
|
||||
|
||||
Safe mode does not necessarily yield safe results when using extensions to Parsedown. Extensions should be evaluated on their own to determine their specific safety against XSS.
|
||||
|
||||
### Escaping HTML
|
||||
> ⚠️ **WARNING:** This method isn't safe from XSS!
|
||||
|
||||
If you wish to escape HTML **in trusted input**, you can use the following:
|
||||
```php
|
||||
$parsedown = new Parsedown;
|
||||
$parsedown->setMarkupEscaped(true);
|
||||
```
|
||||
|
||||
Beware that this still allows users to insert unsafe scripting vectors, such as links like `[xss](javascript:alert%281%29)`.
|
||||
|
||||
### Questions
|
||||
|
||||
**How does Parsedown work?**
|
||||
|
||||
It tries to read Markdown like a human. First, it looks at the lines. It’s interested in how the lines start. This helps it recognise blocks. It knows, for example, that if a line starts with a `-` then perhaps it belongs to a list. Once it recognises the blocks, it continues to the content. As it reads, it watches out for special characters. This helps it recognise inline elements (or inlines).
|
||||
|
||||
We call this approach "line based". We believe that Parsedown is the first Markdown parser to use it. Since the release of Parsedown, other developers have used the same approach to develop other Markdown parsers in PHP and in other languages.
|
||||
|
||||
**Is it compliant with CommonMark?**
|
||||
|
||||
It passes most of the CommonMark tests. Most of the tests that don't pass deal with cases that are quite uncommon. Still, as CommonMark matures, compliance should improve.
|
||||
|
||||
**Who uses it?**
|
||||
|
||||
[Laravel Framework](https://laravel.com/), [Bolt CMS](http://bolt.cm/), [Grav CMS](http://getgrav.org/), [Herbie CMS](http://www.getherbie.org/), [Kirby CMS](http://getkirby.com/), [October CMS](http://octobercms.com/), [Pico CMS](http://picocms.org), [Statamic CMS](http://www.statamic.com/), [phpDocumentor](http://www.phpdoc.org/), [RaspberryPi.org](http://www.raspberrypi.org/), [Symfony demo](https://github.com/symfony/symfony-demo) and [more](https://packagist.org/packages/erusev/parsedown/dependents).
|
||||
|
||||
**How can I help?**
|
||||
|
||||
Use it, star it, share it and if you feel generous, [donate](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=528P3NZQMP8N2).
|
33
public/vendor/erusev/parsedown/composer.json
vendored
Normal file
33
public/vendor/erusev/parsedown/composer.json
vendored
Normal file
@ -0,0 +1,33 @@
|
||||
{
|
||||
"name": "erusev/parsedown",
|
||||
"description": "Parser for Markdown.",
|
||||
"keywords": ["markdown", "parser"],
|
||||
"homepage": "http://parsedown.org",
|
||||
"type": "library",
|
||||
"license": "MIT",
|
||||
"authors": [
|
||||
{
|
||||
"name": "Emanuil Rusev",
|
||||
"email": "hello@erusev.com",
|
||||
"homepage": "http://erusev.com"
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=5.3.0",
|
||||
"ext-mbstring": "*"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "^4.8.35"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-0": {"Parsedown": ""}
|
||||
},
|
||||
"autoload-dev": {
|
||||
"psr-0": {
|
||||
"TestParsedown": "test/",
|
||||
"ParsedownTest": "test/",
|
||||
"CommonMarkTest": "test/",
|
||||
"CommonMarkTestWeak": "test/"
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user