diff --git a/.gitignore b/.gitignore
index e43b0f9..9ab76a1 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1 +1,3 @@
.DS_Store
+*.pyc
+__pycache__
diff --git a/README.md b/README.md
index f6cea1d..d4ea3ac 100644
--- a/README.md
+++ b/README.md
@@ -2,7 +2,7 @@

-An [Alfred 4](https://www.alfredapp.com/) workflow for generating [lorem ipsum](https://en.wikipedia.org/wiki/Lorem_ipsum) dummy text using [joshtronic/php-loremipsum](https://github.com/joshtronic/php-loremipsum).
+An [Alfred 4](https://www.alfredapp.com/) workflow for generating [lorem ipsum](https://en.wikipedia.org/wiki/Lorem_ipsum) dummy text using [JarryShaw/lorem](https://github.com/JarryShaw/lorem).
## Installation
diff --git a/info.plist b/info.plist
index 03f2fbc..8c92359 100644
--- a/info.plist
+++ b/info.plist
@@ -131,7 +131,7 @@
escaping
127
script
- php -f script.php "characters" "{query}"
+ python3 lipsum.py characters {query}
scriptargtype
0
scriptfile
@@ -153,6 +153,8 @@
clipboardtext
{query}
+ ignoredynamicplaceholders
+
transient
@@ -161,7 +163,7 @@
uid
125F91DD-9720-45BD-9F14-08966CFC2643
version
- 2
+ 3
config
@@ -213,7 +215,7 @@
escaping
127
script
- php -f script.php "words" "{query}"
+ python3 lipsum.py words {query}
scriptargtype
0
scriptfile
@@ -228,6 +230,27 @@
version
2
+
+ config
+
+ argumenttype
+ 1
+ keyword
+ lipsum
+ subtext
+ Generate {query} sentences
+ text
+ Sentences
+ withspace
+
+
+ type
+ alfred.workflow.input.keyword
+ uid
+ 1029C7B6-DB95-4448-B3C5-C33F3DA0F894
+ version
+ 1
+
config
@@ -236,7 +259,7 @@
escaping
127
script
- php -f script.php "sentences" "{query}"
+ python3 lipsum.py sentences {query}
scriptargtype
0
scriptfile
@@ -251,27 +274,6 @@
version
2
-
- config
-
- argumenttype
- 1
- keyword
- lipsum
- subtext
- Generate {query} sentences
- text
- Sentences
- withspace
-
-
- type
- alfred.workflow.input.keyword
- uid
- 1029C7B6-DB95-4448-B3C5-C33F3DA0F894
- version
- 1
-
config
@@ -301,7 +303,7 @@
escaping
127
script
- php -f script.php "paragraphs" "{query}"
+ python3 lipsum.py paragraphs {query}
scriptargtype
0
scriptfile
@@ -318,7 +320,7 @@
readme
- An Alfred 3 workflow for generating lorem ipsum dummy text using joshtronic/php-loremipsum.
+ An Alfred 4 workflow for generating lorem ipsum dummy text.
uidata
1029C7B6-DB95-4448-B3C5-C33F3DA0F894
@@ -385,8 +387,10 @@
10
+ variablesdontexport
+
version
- 2.2.0
+ 3.0.0
webaddress
https://github.com/alexchantastic/alfred-lipsum-workflow
diff --git a/lib/LoremIpsum.php b/lib/LoremIpsum.php
deleted file mode 100644
index 69e4de6..0000000
--- a/lib/LoremIpsum.php
+++ /dev/null
@@ -1,372 +0,0 @@
-
- * @copyright Copyright 2014, 2015, 2016, 2017, 2018 Josh Sherman
- * @license http://www.opensource.org/licenses/mit-license.html
- * @link https://github.com/joshtronic/php-loremipsum
- */
-
-namespace joshtronic;
-
-class LoremIpsum
-{
- /**
- * First
- *
- * Whether or not we should be starting the string with "Lorem ipsum..."
- *
- * @access private
- * @var boolean
- */
- private $first = false;
-
- /**
- * Words
- *
- * A lorem ipsum vocabulary of sorts. Not a complete list as I'm unsure if
- * a complete list exists and if so, where to get it.
- *
- * @access private
- * @var array
- */
- public $words = array(
- // Lorem ipsum...
- 'lorem', 'ipsum', 'dolor', 'sit', 'amet', 'consectetur', 'adipiscing', 'elit',
-
- // and the rest of the vocabulary
- 'a', 'ac', 'accumsan', 'ad', 'aenean', 'aliquam', 'aliquet', 'ante',
- 'aptent', 'arcu', 'at', 'auctor', 'augue', 'bibendum', 'blandit',
- 'class', 'commodo', 'condimentum', 'congue', 'consequat', 'conubia',
- 'convallis', 'cras', 'cubilia', 'curabitur', 'curae', 'cursus',
- 'dapibus', 'diam', 'dictum', 'dictumst', 'dignissim', 'dis', 'donec',
- 'dui', 'duis', 'efficitur', 'egestas', 'eget', 'eleifend', 'elementum',
- 'enim', 'erat', 'eros', 'est', 'et', 'etiam', 'eu', 'euismod', 'ex',
- 'facilisi', 'facilisis', 'fames', 'faucibus', 'felis', 'fermentum',
- 'feugiat', 'finibus', 'fringilla', 'fusce', 'gravida', 'habitant',
- 'habitasse', 'hac', 'hendrerit', 'himenaeos', 'iaculis', 'id',
- 'imperdiet', 'in', 'inceptos', 'integer', 'interdum', 'justo',
- 'lacinia', 'lacus', 'laoreet', 'lectus', 'leo', 'libero', 'ligula',
- 'litora', 'lobortis', 'luctus', 'maecenas', 'magna', 'magnis',
- 'malesuada', 'massa', 'mattis', 'mauris', 'maximus', 'metus', 'mi',
- 'molestie', 'mollis', 'montes', 'morbi', 'mus', 'nam', 'nascetur',
- 'natoque', 'nec', 'neque', 'netus', 'nibh', 'nisi', 'nisl', 'non',
- 'nostra', 'nulla', 'nullam', 'nunc', 'odio', 'orci', 'ornare',
- 'parturient', 'pellentesque', 'penatibus', 'per', 'pharetra',
- 'phasellus', 'placerat', 'platea', 'porta', 'porttitor', 'posuere',
- 'potenti', 'praesent', 'pretium', 'primis', 'proin', 'pulvinar',
- 'purus', 'quam', 'quis', 'quisque', 'rhoncus', 'ridiculus', 'risus',
- 'rutrum', 'sagittis', 'sapien', 'scelerisque', 'sed', 'sem', 'semper',
- 'senectus', 'sociosqu', 'sodales', 'sollicitudin', 'suscipit',
- 'suspendisse', 'taciti', 'tellus', 'tempor', 'tempus', 'tincidunt',
- 'torquent', 'tortor', 'tristique', 'turpis', 'ullamcorper', 'ultrices',
- 'ultricies', 'urna', 'ut', 'varius', 'vehicula', 'vel', 'velit',
- 'venenatis', 'vestibulum', 'vitae', 'vivamus', 'viverra', 'volutpat',
- 'vulputate',
- );
-
- /**
- * Word
- *
- * Generates a single word of lorem ipsum.
- *
- * @access public
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @return string generated lorem ipsum word
- */
- public function word($tags = false)
- {
- return $this->words(1, $tags);
- }
-
- /**
- * Words Array
- *
- * Generates an array of lorem ipsum words.
- *
- * @access public
- * @param integer $count how many words to generate
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @return array generated lorem ipsum words
- */
- public function wordsArray($count = 1, $tags = false)
- {
- return $this->words($count, $tags, true);
- }
-
- /**
- * Words
- *
- * Generates words of lorem ipsum.
- *
- * @access public
- * @param integer $count how many words to generate
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @param boolean $array whether an array or a string should be returned
- * @return mixed string or array of generated lorem ipsum words
- */
- public function words($count = 1, $tags = false, $array = false)
- {
- $words = array();
- $word_count = 0;
-
- // Shuffles and appends the word list to compensate for count
- // arguments that exceed the size of our vocabulary list
- while ($word_count < $count) {
- $shuffle = true;
-
- while ($shuffle) {
- $this->shuffle();
-
- // Checks that the last word of the list and the first word of
- // the list that's about to be appended are not the same
- if (!$word_count || $words[$word_count - 1] != $this->words[0]) {
- $words = array_merge($words, $this->words);
- $word_count = count($words);
- $shuffle = false;
- }
- }
- }
-
- $words = array_slice($words, 0, $count);
-
- return $this->output($words, $tags, $array);
- }
-
- /**
- * Sentence
- *
- * Generates a full sentence of lorem ipsum.
- *
- * @access public
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @return string generated lorem ipsum sentence
- */
- public function sentence($tags = false)
- {
- return $this->sentences(1, $tags);
- }
-
- /**
- * Sentences Array
- *
- * Generates an array of lorem ipsum sentences.
- *
- * @access public
- * @param integer $count how many sentences to generate
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @return array generated lorem ipsum sentences
- */
- public function sentencesArray($count = 1, $tags = false)
- {
- return $this->sentences($count, $tags, true);
- }
-
- /**
- * Sentences
- *
- * Generates sentences of lorem ipsum.
- *
- * @access public
- * @param integer $count how many sentences to generate
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @param boolean $array whether an array or a string should be returned
- * @return mixed string or array of generated lorem ipsum sentences
- */
- public function sentences($count = 1, $tags = false, $array = false)
- {
- $sentences = array();
-
- for ($i = 0; $i < $count; $i++) {
- $sentences[] = $this->wordsArray($this->gauss(24.46, 5.08));
- }
-
- $this->punctuate($sentences);
-
- return $this->output($sentences, $tags, $array);
- }
-
- /**
- * Paragraph
- *
- * Generates a full paragraph of lorem ipsum.
- *
- * @access public
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @return string generated lorem ipsum paragraph
- */
- public function paragraph($tags = false)
- {
- return $this->paragraphs(1, $tags);
- }
-
- /**
- * Paragraph Array
- *
- * Generates an array of lorem ipsum paragraphs.
- *
- * @access public
- * @param integer $count how many paragraphs to generate
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @return array generated lorem ipsum paragraphs
- */
- public function paragraphsArray($count = 1, $tags = false)
- {
- return $this->paragraphs($count, $tags, true);
- }
-
- /**
- * Paragraphss
- *
- * Generates paragraphs of lorem ipsum.
- *
- * @access public
- * @param integer $count how many paragraphs to generate
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @param boolean $array whether an array or a string should be returned
- * @return mixed string or array of generated lorem ipsum paragraphs
- */
- public function paragraphs($count = 1, $tags = false, $array = false)
- {
- $paragraphs = array();
-
- for ($i = 0; $i < $count; $i++) {
- $paragraphs[] = $this->sentences($this->gauss(5.8, 1.93));
- }
-
- return $this->output($paragraphs, $tags, $array, "\n\n");
- }
-
- /**
- * Gaussian Distribution
- *
- * This is some smart kid stuff. I went ahead and combined the N(0,1) logic
- * with the N(m,s) logic into this single function. Used to calculate the
- * number of words in a sentence, the number of sentences in a paragraph
- * and the distribution of commas in a sentence.
- *
- * @access private
- * @param double $mean average value
- * @param double $std_dev stadnard deviation
- * @return double calculated distribution
- */
- private function gauss($mean, $std_dev)
- {
- $x = mt_rand() / mt_getrandmax();
- $y = mt_rand() / mt_getrandmax();
- $z = sqrt(-2 * log($x)) * cos(2 * pi() * $y);
-
- return $z * $std_dev + $mean;
- }
-
- /**
- * Shuffle
- *
- * Shuffles the words, forcing "Lorem ipsum..." at the beginning if it is
- * the first time we are generating the text.
- *
- * @access private
- */
- private function shuffle()
- {
- if ($this->first) {
- $this->first = array_slice($this->words, 0, 8);
- $this->words = array_slice($this->words, 8);
-
- shuffle($this->words);
-
- $this->words = $this->first + $this->words;
-
- $this->first = false;
- } else {
- shuffle($this->words);
- }
- }
-
- /**
- * Punctuate
- *
- * Applies punctuation to a sentence. This includes a period at the end,
- * the injection of commas as well as capitalizing the first letter of the
- * first word of the sentence.
- *
- * @access private
- * @param array $sentences the sentences we would like to punctuate
- */
- private function punctuate(&$sentences)
- {
- foreach ($sentences as $key => $sentence) {
- $words = count($sentence);
-
- // Only worry about commas on sentences longer than 4 words
- if ($words > 4) {
- $mean = log($words, 6);
- $std_dev = $mean / 6;
- $commas = round($this->gauss($mean, $std_dev));
-
- for ($i = 1; $i <= $commas; $i++) {
- $word = round($i * $words / ($commas + 1));
-
- if ($word < ($words - 1) && $word > 0) {
- $sentence[$word] .= ',';
- }
- }
- }
-
- $sentences[$key] = ucfirst(implode(' ', $sentence) . '.');
- }
- }
-
- /**
- * Output
- *
- * Does the rest of the processing of the strings. This includes wrapping
- * the strings in HTML tags, handling transformations with the ability of
- * back referencing and determining if the passed array should be converted
- * into a string or not.
- *
- * @access private
- * @param array $strings an array of generated strings
- * @param mixed $tags string or array of HTML tags to wrap output with
- * @param boolean $array whether an array or a string should be returned
- * @param string $delimiter the string to use when calling implode()
- * @return mixed string or array of generated lorem ipsum text
- */
- private function output($strings, $tags, $array, $delimiter = ' ')
- {
- if ($tags) {
- if (!is_array($tags)) {
- $tags = array($tags);
- } else {
- // Flips the array so we can work from the inside out
- $tags = array_reverse($tags);
- }
-
- foreach ($strings as $key => $string) {
- foreach ($tags as $tag) {
- // Detects / applies back reference
- if ($tag[0] == '<') {
- $string = str_replace('$1', $string, $tag);
- } else {
- $string = sprintf('<%1$s>%2$s%1$s>', $tag, $string);
- }
-
- $strings[$key] = $string;
- }
- }
- }
-
- if (!$array) {
- $strings = implode($delimiter, $strings);
- }
-
- return $strings;
- }
-}
diff --git a/lib/__init__.py b/lib/__init__.py
new file mode 100644
index 0000000..e69de29
diff --git a/lib/lorem/LICENSE b/lib/lorem/LICENSE
new file mode 100755
index 0000000..be383ed
--- /dev/null
+++ b/lib/lorem/LICENSE
@@ -0,0 +1,29 @@
+BSD 3-Clause License
+
+Copyright (c) 2019, Jarry Shaw
+All rights reserved.
+
+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/lib/lorem/__init__.py b/lib/lorem/__init__.py
new file mode 100644
index 0000000..e69de29
diff --git a/lib/lorem/lorem.py b/lib/lorem/lorem.py
new file mode 100755
index 0000000..5299264
--- /dev/null
+++ b/lib/lorem/lorem.py
@@ -0,0 +1,436 @@
+# -*- coding: utf-8 -*-
+"""lorem ipsum generator
+
+In publishing and graphic design, lorem ipsum is a placeholder text commonly
+used to demonstrate the visual form of a document or a typeface without
+relying on meaningful content.
+
+The :mod:`lorem` module provides a generic access to generating the lorem ipsum
+text from its very original text::
+
+ Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod
+ tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim
+ veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea
+ commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit
+ esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat
+ cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id
+ est laborum.
+
+Usage of the :mod:`lorem` module is rather simple. Depending on your needs, the
+:mod:`lorem` module provides generation of *words*, *sentences*, and
+*paragraphs*.
+
+Get Random Words
+----------------
+
+The :mod:`lorem` module provides two different ways for getting random words.
+
+1. :func:`word` -- generate a list of random words
+
+ .. code:: python
+
+ word(count=1, func=None, args=(), kwargs={}) -> Iterator[str]
+
+2. :func:`get_word` -- return random words
+
+ .. code:: python
+
+ get_word(count=1, sep=' ', func=None, args=(), kwargs={}) -> str
+
+Get Random Sentences
+--------------------
+
+The :mod:`lorem` module provides two different ways for getting random sentences.
+
+1. :func:`sentence` -- generate a list of random sentences
+
+ .. code:: python
+
+ sentence(count=1, comma=(0, 2), word_range=(4, 8)) -> Iterator[str]
+
+2. :func:`get_sentence` -- return random sentences
+
+ .. code :: python
+
+ get_sentence(count=1, sep=' ', comma=(0, 2), word_range=(4, 8)) -> Union[str]
+
+Get Random Paragraphs
+---------------------
+
+The :mod:`lorem` module provides two different ways for getting random paragraphs.
+
+1. :func:`paragraph` -- generate a list of random paragraphs
+
+ .. code:: python
+
+ paragraph(count=1, comma=(0, 2), word_range=(4, 8), sentence_range=(5, 10)) -> Iterator[str]
+
+2. :func:`get_paragraph` -- return random paragraphs
+
+ .. code:: python
+
+ get_paragraph(count=1, sep=os.linesep, comma=(0, 2), word_range=(4, 8), sentence_range=(5, 10)) -> Union[str]
+
+Customise Word Pool
+-------------------
+
+If wanted, the :mod:`lorem` module also provides an interface to customise the word
+pool as you wish.
+
+1. :func:`set_pool` -- customise random word pool
+
+ .. code:: python
+
+ set_pool(pool)
+
+"""
+import itertools
+import os
+import random
+import typing
+
+__all__ = [
+ 'set_pool',
+ 'word', 'sentence', 'paragraph',
+ 'get_word', 'get_sentence', 'get_paragraph',
+]
+
+#: The original lorem ipsum text pool.
+_TEXT = ('ad', 'adipiscing', 'aliqua', 'aliquip', 'amet', 'anim', 'aute', 'cillum', 'commodo',
+ 'consectetur', 'consequat', 'culpa', 'cupidatat', 'deserunt', 'do', 'dolor', 'dolore',
+ 'duis', 'ea', 'eiusmod', 'elit', 'enim', 'esse', 'est', 'et', 'eu', 'ex', 'excepteur',
+ 'exercitation', 'fugiat', 'id', 'in', 'incididunt', 'ipsum', 'irure', 'labore', 'laboris',
+ 'laborum', 'lorem', 'magna', 'minim', 'mollit', 'nisi', 'non', 'nostrud', 'nulla',
+ 'occaecat', 'officia', 'pariatur', 'proident', 'qui', 'quis', 'reprehenderit', 'sed',
+ 'sint', 'sit', 'sunt', 'tempor', 'ullamco', 'ut', 'velit', 'veniam', 'voluptate')
+
+
+def _gen_pool(dupe: int = 1) -> typing.Iterator[str]:
+ """Generate word pool.
+
+ Args:
+ dupe (int): Duplication to generate the word pool.
+
+ Returns:
+ :obj:`Iterator[str]`: An infinite loop word pool.
+
+ """
+ pool = list()
+ for _ in range(dupe):
+ pool.extend(_TEXT)
+ random.shuffle(pool)
+
+ while pool: # pragma: no cover
+ for text in pool:
+ yield text
+ random.shuffle(pool)
+
+
+def _gen_word(pool: typing.Iterator[str], # pylint: disable=dangerous-default-value
+ func: typing.Optional[typing.Union[str, typing.Callable[[str], str]]] = None,
+ args: typing.Tuple[str] = (), kwargs: typing.Dict[str, str] = {}) -> str:
+ """Generate random word.
+
+ Args:
+ pool (:obj:`Iterator[str]`): Word pool, returned by :func:`_gen_pool`.
+ func (:obj:`Optional[Union[str, Callable[[str], str]]]`): Filter function. It can be an
+ attribute name of :obj:`str`, or a customised function that takes the original :obj:`str`
+ and returns the modified :obj:`str`.
+ args (:obj:`Tuple[str]`): Additional positional arguments for ``func``.
+ kwargs (:obj:`Dict[str, Any]`): Additional keyword arguments for ``func``.
+
+ Returns:
+ :obj:`str`: Random word.
+
+ """
+ text = next(pool)
+ if func is not None:
+ if isinstance(func, str):
+ text = getattr(text, func)(*args, **kwargs)
+ else:
+ text = func(text, *args, **kwargs)
+ return text
+
+
+def _gen_sentence(pool: typing.Iterator[str],
+ comma: typing.Tuple[int],
+ word_range: typing.Tuple[int]) -> str:
+ """Generate random sentence.
+
+ Args:
+ pool (:obj:`Iterator[str]`): Word pool, returned by :func:`_gen_pool`.
+ comma (:obj:`Tuple[int]`): Random range for number of commas. The function will use
+ :func:`random.randint` to choose a random integer as the number of commas.
+ word_range (:obj:`Tuple[int]`): Random range for number of words in each sentence.
+ The function will use :func:`random.randint` to choose a random integer as the
+ number of words.
+
+ Returns:
+ :obj:`str`: Random sentence.
+
+ """
+ text = _gen_word(pool=pool, func='capitalize')
+ for _ in range(random.randint(*word_range) - 1):
+ text += ' ' + _gen_word(pool=pool)
+
+ for _ in range(random.randint(*comma)):
+ include_comma = random.choice([True, False])
+ if include_comma:
+ text += ','
+ for _ in range(random.randint(*word_range)):
+ text += ' ' + _gen_word(pool=pool)
+ continue
+ break
+ return text + '.'
+
+
+def _gen_paragraph(pool: typing.Iterator[str],
+ comma: typing.Tuple[int],
+ word_range: typing.Tuple[int],
+ sentence_range: typing.Tuple[int]) -> str:
+ """Generate random paragraph.
+
+ Args:
+ pool (:obj:`Iterator[str]`): Word pool, returned by :func:`_gen_pool`.
+ comma (:obj:`Tuple[int]`): Random range for number of commas. The function will use
+ :func:`random.randint` to choose a random integer as the number of commas.
+ word_range (:obj:`Tuple[int]`): Random range for number of words in each sentence.
+ The function will use :func:`random.randint` to choose a random integer as the
+ number of words.
+ sentence_range (:obj:`Tuple[int]`): Random range for number of sentences in each
+ paragraph. The function will use :func:`random.randint` to choose a random integer
+ as the number of sentences.
+
+ Returns:
+ :obj:`str`: Random paragraph.
+
+ """
+ text = _gen_sentence(pool=pool, comma=comma, word_range=word_range)
+ for _ in range(random.randint(*sentence_range) - 1):
+ text += ' ' + _gen_sentence(pool=pool, comma=comma, word_range=word_range)
+ return text
+
+
+def word(count: int = 1, # pylint: disable=dangerous-default-value
+ func: typing.Optional[typing.Union[str, typing.Callable[[str], str]]] = None,
+ args: typing.Tuple[str] = (), kwargs: typing.Dict[str, str] = {}) -> typing.Iterator[str]:
+ """Generate a list of random words.
+
+ .. code:: python
+
+ >>> list(itertools.cycle(word(count=3), 3))
+ ['labore', 'tempor', 'commodo']
+ >>> list(itertools.cycle(word(count=3, func='capitalize'), 3))
+ ['Ea', 'Lorem', 'Do']
+ >>> list(itertools.cycle(word(count=3, func=lambda s: s.upper()), 3))
+ ['UT', 'AMET', 'EXCEPTEUR']
+
+ Args:
+ count (int): Number of non-repeated random words.
+ func (:obj:`Optional[Union[str, Callable[[str], str]]]`): Filter function.
+ It can be an attribute name of :obj:`str`, or a customised function that
+ takes the original :obj:`str` and returns the modified :obj:`str`.
+ args (:obj:`Tuple[str]`): Additional positional arguments for ``func``.
+ kwargs (:obj:`Dict[str, Any]`): Additional keyword arguments for ``func``.
+
+ Returns:
+ :obj:`Iterator[str]`: Indefinite random words generator.
+
+ """
+ pool = _gen_pool(count)
+ yield from itertools.cycle(_gen_word(pool=pool,
+ func=func,
+ args=args,
+ kwargs=kwargs) for _ in range(count))
+
+
+def sentence(count: int = 1,
+ comma: typing.Tuple[int] = (0, 2),
+ word_range: typing.Tuple[int] = (4, 8)) -> typing.Iterator[str]:
+ """Generate a list of random sentences.
+
+ .. code:: python
+
+ >>> list(itertools.islice(sentence(), 1))
+ ['Aute irure et commodo sunt do duis dolor.']
+
+ Args:
+ count (int): Number of non-repeated random sentences.
+ comma (:obj:`Tuple[int]`): Random range for number of commas. The function will
+ use :func:`random.randint` to choose a random integer as the number of commas.
+ word_range (:obj:`Tuple[int]`): Random range for number of words in each sentence.
+ The function will use :func:`random.randint` to choose a random integer as the
+ number of words.
+
+ Returns:
+ :obj:`Iterator[str]`: Indefinite random sentence generator.
+
+ """
+ pool = _gen_pool(count * random.randint(*word_range))
+ yield from itertools.cycle(_gen_sentence(pool=pool,
+ comma=comma,
+ word_range=word_range) for _ in range(count))
+
+
+def paragraph(count: int = 1,
+ comma: typing.Tuple[int] = (0, 2),
+ word_range: typing.Tuple[int] = (4, 8),
+ sentence_range: typing.Tuple[int] = (5, 10)) -> typing.Iterator[str]:
+ """Generate a list of random paragraphs.
+
+ .. code:: python
+
+ >>> list(itertools.islice(paragraph(), 1))
+ ['Aute sint et cupidatat aliquip. Non exercitation est aliquip voluptate '
+ 'fugiat, reprehenderit ad occaecat laboris velit consequat. Magna enim '
+ 'deserunt aute laborum fugiat exercitation. Aliqua ex sunt fugiat in '
+ 'magna voluptate. Elit nisi exercitation nostrud. Magna proident et '
+ 'fugiat eiusmod cupidatat fugiat, sit culpa fugiat non ea eu '
+ 'reprehenderit elit. Proident mollit mollit ut cillum. Nostrud voluptate '
+ 'aliquip cupidatat anim.']
+
+ Args:
+ count (int): Number of non-repeated random paragraphs.
+ comma (:obj:`Tuple[int]`): Random range for number of commas. The function
+ will use :func:`random.randint` to choose a random integer as the number
+ of commas.
+ word_range (:obj:`Tuple[int]`): Random range for number of words in each sentence.
+ The function will use :func:`random.randint` to choose a random integer as the
+ number of words.
+ sentence_range (:obj:`Tuple[int]`): Random range for number of sentences in each
+ paragraph. The function will use :func:`random.randint` to choose a random
+ integer as the number of sentences.
+
+ Returns:
+ :obj:`Iterator[str]`: Random paragraph generator.
+
+ """
+ pool = _gen_pool(count * random.randint(*word_range) * random.randint(*sentence_range))
+ yield from itertools.cycle(_gen_paragraph(pool=pool,
+ comma=comma,
+ word_range=word_range,
+ sentence_range=sentence_range) for _ in range(count))
+
+
+def get_word(count: typing.Union[int, typing.Tuple[int]] = 1, # pylint: disable=dangerous-default-value
+ sep: str = ' ',
+ func: typing.Optional[typing.Union[str, typing.Callable[[str], str]]] = None,
+ args: typing.Tuple[str] = (), kwargs: typing.Dict[str, str] = {}) -> str:
+ """Return random words.
+
+ .. code:: python
+
+ >>> get_word(count=3)
+ 'anim voluptate non'
+ >>> get_word(count=3, func='capitalize')
+ 'Non Labore Ut'
+ >>> get_word(count=3, func=lambda s: s.upper())
+ 'NISI TEMPOR CILLUM'
+
+ Args:
+ count (:obj:`Union[int, Tuple[int]]`): Number of random words. To generate random
+ number of words, supply a 2-element tuple of :obj:`int`, the function will use
+ :func:`random.randint` to choose a random integer as the number of random words.
+ sep (str): Seperator between each word.
+ func (:obj:`Optional[Union[str, Callable[[str], str]]]`): Filter function. It can be
+ a function name of :obj:`str`, or a customised function that takes the original
+ :obj:`str` and returns the modified :obj:`str`.
+ args (:obj:`Tuple[str]`): Additional positional arguments for ``func``.
+ kwargs (:obj:`Dict[str, Any]`): Additional keyword arguments for ``func``.
+
+ Returns:
+ :obj:`str`: Random words.
+
+ """
+ if isinstance(count, tuple):
+ count = random.randint(*count)
+ return sep.join(itertools.islice(word(count, func, args, kwargs), count))
+
+
+def get_sentence(count: typing.Union[int, typing.Tuple[int]] = 1,
+ sep: str = ' ',
+ comma: typing.Tuple[int] = (0, 2),
+ word_range: typing.Tuple[int] = (4, 8)) -> str:
+ """Return random sentences.
+
+ .. code:: python
+
+ >>> get_sentence()
+ 'Nostrud laboris lorem minim sit culpa, aliqua nostrud in amet, sint pariatur eiusmod esse.'
+
+ Args:
+
+ count (:obj:`Union[int, Tuple[int]]`): Number of random sentences. To generate
+ random number of sentences, supply a 2-element tuple of :obj:`int`, the
+ function will use :func:`random.randint` to choose a random integer as the number
+ of random sentences.
+ sep (str): Seperator between each sentence.
+ comma (:obj:`Tuple[int]`): Random range for number of commas. The function will use
+ :func:`random.randint` to choose a random integer as the number of commas.
+ word_range (:obj:`Tuple[int]`): Random range for number of words in each sentence.
+ The function will use :func:`random.randint` to choose a random integer as the
+ number of words.
+
+ Returns:
+ :obj:`str`: Random sentences.
+
+ """
+ if isinstance(count, tuple):
+ count = random.randint(*count)
+ return sep.join(itertools.islice(sentence(count, comma, word_range), count))
+
+
+def get_paragraph(count: typing.Union[int, typing.Tuple[int]] = 1,
+ sep: str = os.linesep,
+ comma: typing.Tuple[int] = (0, 2),
+ word_range: typing.Tuple[int] = (4, 8),
+ sentence_range: typing.Tuple[int] = (5, 10)) -> str:
+ """Return random paragraphs.
+
+ .. code:: python
+
+ >>> get_paragraph()
+ 'Exercitation magna sunt excepteur irure adipiscing commodo duis. Est '
+ 'ipsum qui deserunt, deserunt nostrud reprehenderit esse. Do velit '
+ 'est in velit sed. Sunt officia officia lorem. Commodo lorem '
+ 'exercitation veniam officia pariatur velit. Deserunt deserunt sed '
+ 'consequat laborum consequat dolor. Et consectetur irure sint elit tempor,'
+ ' est minim nisi eiusmod id excepteur. Minim cillum veniam sed aliquip '
+ 'anim sit, pariatur nostrud ex cillum laboris laborum. Laborum ullamco '
+ 'mollit elit. Amet id incididunt ipsum sed.'
+
+ Args:
+ count (:obj:`Union[int, Tuple[int]]`): Number of random paragraphs. To generate
+ random number of paragraphs, supply a 2-element tuple of :obj:`int`, the function
+ will use :func:`random.randint` to choose a random integer as the number of random
+ paragraphs.
+ sep (str): Seperator between each paragraph. The default value is OS-dependent as
+ :data:`os.linsep` (``\\r\\n`` on Windows, ``\\n`` on POSIX).
+ comma (:obj:`Tuple[int]`): Random range for number of commas. The function will use
+ :func:`random.randint` to choose a random integer as the number of commas.
+ word_range (:obj:`Tuple[int]`): Random range for number of words in each sentence.
+ The function will use :func:`random.randint` to choose a random integer as the
+ number of words.
+ sentence_range (:obj:`Tuple[int]`): Random range for number of sentences in each
+ paragraph. The function will use :func:`random.randint` to choose a random integer
+ as the number of sentences.
+
+ Returns:
+ :obj:`str`: Random paragraphs.
+
+ """
+ if isinstance(count, tuple):
+ count = random.randint(*count)
+ return sep.join(itertools.islice(paragraph(count, comma, word_range, sentence_range), count))
+
+
+def set_pool(pool: typing.Iterable[str]):
+ """Customise random word pool.
+
+ Args:
+
+ pool (:obj:`Iterable[str]`): List of words to be used as random word pool.
+
+ """
+ global _TEXT
+ _TEXT = pool
diff --git a/lipsum.py b/lipsum.py
new file mode 100644
index 0000000..056a14c
--- /dev/null
+++ b/lipsum.py
@@ -0,0 +1,32 @@
+import sys
+from lib.lorem import lorem
+
+args = sys.argv
+type = args[1]
+count = int(args[2]) if len(args) >= 3 else 1
+
+def get_character(count):
+ pool = lorem.get_word(1)
+
+ while len(pool) <= count:
+ pool += ' ' + lorem.get_word(1)
+
+ return pool[0:count]
+
+def lipsum(type):
+ if type == 'characters':
+ return get_character(count).capitalize()
+
+ elif type == 'words':
+ return lorem.get_word(count).capitalize()
+
+ elif type == 'sentences':
+ return lorem.get_sentence(count)
+
+ elif type == 'paragraphs':
+ return lorem.get_paragraph(count, '\n\n')
+
+ else:
+ return lorem.get_sentence(count)
+
+print(lipsum(type))
diff --git a/script.php b/script.php
deleted file mode 100644
index 89905bf..0000000
--- a/script.php
+++ /dev/null
@@ -1,66 +0,0 @@
-word();
- $word_length = strlen($word);
-
- if ($word !== $words_array[$words_count - 1]) {
- $character_count += $word_length + count($words_array);
-
- array_push($words_array, $word);
-
- $words_count = count($words_array);
- }
- }
-
- $words = implode(' ', $words_array);
- $words = substr($words, 0, $count);
-
- $last_character = substr($words, -1);
-
- if ($last_character === ' ') {
- $words = substr($words, 0, -1) . substr($lipsum->word(), 0, 1);
- }
-
- return $words;
-}
-
-switch ($type) {
- case 'characters':
- $output = characters($length);
- break;
- case 'words':
- $output = $lipsum->words($length);
- break;
- case 'sentences':
- $output = $lipsum->sentences($length);
- break;
- case 'paragraphs':
- $output = $lipsum->paragraphs($length);
- break;
-}
-
-echo ucfirst($output);
\ No newline at end of file