Compare commits
215 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
361c96d746 | ||
|
|
e7dbf9278d | ||
|
|
6564fddb27 | ||
|
|
d382874e86 | ||
|
|
91b30bee9f | ||
|
|
7804aad776 | ||
|
|
b7552ac8aa | ||
|
|
a76c94cccf | ||
|
|
c0ae5c7cad | ||
|
|
cc55b39b83 | ||
|
|
d8a6884ab6 | ||
|
|
5ce3581386 | ||
|
|
2208f2a8c0 | ||
|
|
a4a14c7e63 | ||
|
|
aa464b476c | ||
|
|
3c92712a6e | ||
|
|
fd0c47f5d7 | ||
|
|
c03a44d225 | ||
|
|
d31d45ba71 | ||
|
|
db528b27f4 | ||
|
|
e6d29f6f18 | ||
|
|
e4d6b988ef | ||
|
|
ec68291bf0 | ||
|
|
3a6a451db1 | ||
|
|
7ec095d708 | ||
|
|
57f6206aee | ||
|
|
390f10e83f | ||
|
|
8727935cb2 | ||
|
|
d0e868f556 | ||
|
|
01c357e146 | ||
|
|
a0fed4a9d0 | ||
|
|
c4aed0ec89 | ||
|
|
cc737090a2 | ||
|
|
1652c09e95 | ||
|
|
2538b88579 | ||
|
|
8c2eb63840 | ||
|
|
36df5ee6e4 | ||
|
|
9720b4edf1 | ||
|
|
13d35b7607 | ||
|
|
13c2c51cfd | ||
|
|
f43175b0c3 | ||
|
|
1508aba8b2 | ||
|
|
5414ab05e5 | ||
|
|
bd5d2db634 | ||
|
|
3259dd29d8 | ||
|
|
6e56013a95 | ||
|
|
252f762209 | ||
|
|
15c0448cf1 | ||
|
|
4c800bacaa | ||
|
|
5902a483b4 | ||
|
|
ca73e4b93e | ||
|
|
ace64d88ce | ||
|
|
4cc9f7c8b5 | ||
|
|
f4f1390b67 | ||
|
|
14115761f9 | ||
|
|
ac3409e376 | ||
|
|
86a73229c0 | ||
|
|
cc41b96e88 | ||
|
|
e16c5584d1 | ||
|
|
94bab3f550 | ||
|
|
9d04b23fb2 | ||
|
|
2657e5050f | ||
|
|
3d6e5b2b9e | ||
|
|
bdd6b9727d | ||
|
|
6c8172c7cf | ||
|
|
ae5bae9899 | ||
|
|
b6bf306042 | ||
|
|
9c5196dfec | ||
|
|
3d7b8592ea | ||
|
|
e03f7691f2 | ||
|
|
7a54ac62d6 | ||
|
|
8db06d37d2 | ||
|
|
5ee5e76544 | ||
|
|
090cd999cb | ||
|
|
50b75354e0 | ||
|
|
c7b6b25851 | ||
|
|
b931df654d | ||
|
|
b5d5c4177d | ||
|
|
b22550ea55 | ||
|
|
04d50ebea5 | ||
|
|
202180909c | ||
|
|
0d806e6d74 | ||
|
|
54f31ebe7f | ||
|
|
227a39d2fa | ||
|
|
99d8faa38b | ||
|
|
9a7afe1549 | ||
|
|
e6751e0d89 | ||
|
|
371f1df830 | ||
|
|
8e1ba352ee | ||
|
|
7ebfe42eb2 | ||
|
|
df514d3b9f | ||
|
|
acae16e7ee | ||
|
|
deb8508ea5 | ||
|
|
a4bbf41086 | ||
|
|
4fbc535b0c | ||
|
|
36f6f98ce7 | ||
|
|
21cc7d604c | ||
|
|
44207161e6 | ||
|
|
dc20ef0754 | ||
|
|
413ee7a6d3 | ||
|
|
5b94714ca7 | ||
|
|
3675fe1ed7 | ||
|
|
e074a03c40 | ||
|
|
a7860f72a2 | ||
|
|
4b587593ee | ||
|
|
0aa8a97070 | ||
|
|
3c16f84853 | ||
|
|
346898e549 | ||
|
|
bcef4b2de7 | ||
|
|
e42bf7fd7c | ||
|
|
48cd0602d8 | ||
|
|
814e837ae5 | ||
|
|
a58b34eba8 | ||
|
|
7d790f8f79 | ||
|
|
7cf06f4989 | ||
|
|
61381b7168 | ||
|
|
df598c5900 | ||
|
|
aed74e029a | ||
|
|
6e01e1b9da | ||
|
|
42f278aafe | ||
|
|
884f64addb | ||
|
|
0c9cf4ddd5 | ||
|
|
f6dfe0e8dd | ||
|
|
9f4ca1add7 | ||
|
|
1f6edc5852 | ||
|
|
a74017f595 | ||
|
|
89bc7609ea | ||
|
|
2c93c8ef6d | ||
|
|
bfe370fa50 | ||
|
|
3b4850e1ba | ||
|
|
b2d1c25b8e | ||
|
|
093598ac99 | ||
|
|
585d22be46 | ||
|
|
9361cf4b00 | ||
|
|
298e9130dd | ||
|
|
41ae47f065 | ||
|
|
41f7fe1554 | ||
|
|
965be1c0f3 | ||
|
|
fa8ac37e8b | ||
|
|
d7975b6192 | ||
|
|
0a0fe55427 | ||
|
|
8e08a20178 | ||
|
|
9dd44808ec | ||
|
|
507cf1d511 | ||
|
|
53f3ce8b1f | ||
|
|
2d39e5b1fa | ||
|
|
60716dcf81 | ||
|
|
82141c2535 | ||
|
|
3d6de3fe75 | ||
|
|
03ab396353 | ||
|
|
6221601376 | ||
|
|
71fdef45c9 | ||
|
|
147a9e4968 | ||
|
|
8f7b56da32 | ||
|
|
4ef2452083 | ||
|
|
70cfa03ee8 | ||
|
|
5bd3d4fd96 | ||
|
|
c0fe02efb9 | ||
|
|
b0f4843526 | ||
|
|
a9e161268c | ||
|
|
cbad8857bd | ||
|
|
5adefda286 | ||
|
|
265bfcd7c8 | ||
|
|
b81a4987d9 | ||
|
|
6b9c9eb0ed | ||
|
|
4f82d618dc | ||
|
|
b7f7bdb9ac | ||
|
|
c5136fd330 | ||
|
|
e7e0e886fc | ||
|
|
42e8ab1680 | ||
|
|
ab7b7de60a | ||
|
|
21221d48d0 | ||
|
|
1f1a190c84 | ||
|
|
82d79c4662 | ||
|
|
08771a6d5d | ||
|
|
e01d18f224 | ||
|
|
8496650542 | ||
|
|
399245cd0f | ||
|
|
adfa5dddcf | ||
|
|
85971e0e91 | ||
|
|
3a3376ec41 | ||
|
|
d988b6ccbf | ||
|
|
6654f446a4 | ||
|
|
88808db9a5 | ||
|
|
dfad0fd6bd | ||
|
|
3fe49a24c7 | ||
|
|
ac609445fb | ||
|
|
0223f74a53 | ||
|
|
607a5b3fda | ||
|
|
e3ac331a71 | ||
|
|
e09b4cc76d | ||
|
|
c24ed707ef | ||
|
|
a8c55ddee3 | ||
|
|
e080835224 | ||
|
|
2fe675abce | ||
|
|
d230221999 | ||
|
|
91a01265e5 | ||
|
|
77286301a7 | ||
|
|
7c39827c16 | ||
|
|
8f789994eb | ||
|
|
79cb9c8142 | ||
|
|
de1d047c08 | ||
|
|
8252cb486b | ||
|
|
fb8ad72335 | ||
|
|
bc4f0c002b | ||
|
|
0a53c52645 | ||
|
|
7941a8accb | ||
|
|
5389923b34 | ||
|
|
9c1149cb25 | ||
|
|
c5130de805 | ||
|
|
020633503b | ||
|
|
74b9776801 | ||
|
|
5a605d686c | ||
|
|
4ba9bdf605 | ||
|
|
3f647348c3 |
1
.gitignore
vendored
1
.gitignore
vendored
@@ -12,3 +12,4 @@ log.txt
|
||||
debug.log
|
||||
wordlist.txt
|
||||
rspec_results.html
|
||||
data/
|
||||
|
||||
@@ -1 +1 @@
|
||||
2.1.3
|
||||
2.2.3
|
||||
|
||||
17
.travis.yml
17
.travis.yml
@@ -1,4 +1,6 @@
|
||||
language: ruby
|
||||
sudo: false
|
||||
cache: bundler
|
||||
rvm:
|
||||
- 1.9.2
|
||||
- 1.9.3
|
||||
@@ -6,10 +8,23 @@ rvm:
|
||||
- 2.1.0
|
||||
- 2.1.1
|
||||
- 2.1.2
|
||||
- 2.1.3
|
||||
- 2.1.4
|
||||
- 2.1.5
|
||||
- 2.2.0
|
||||
- 2.2.1
|
||||
- 2.2.2
|
||||
- 2.2.3
|
||||
before_install:
|
||||
- "echo 'gem: --no-ri --no-rdoc' > ~/.gemrc"
|
||||
script: bundle exec rspec
|
||||
notifications:
|
||||
email:
|
||||
- wpscanteam@gmail.com
|
||||
- team@wpscan.org
|
||||
matrix:
|
||||
allow_failures:
|
||||
- rvm: 1.9.2
|
||||
# do not build gh-pages branch
|
||||
branches:
|
||||
except:
|
||||
- gh-pages
|
||||
|
||||
170
CHANGELOG.md
170
CHANGELOG.md
@@ -1,6 +1,174 @@
|
||||
# Changelog
|
||||
## Master
|
||||
[Work in progress](https://github.com/wpscanteam/wpscan/compare/2.5.1...master)
|
||||
[Work in progress](https://github.com/wpscanteam/wpscan/compare/2.9...master)
|
||||
|
||||
## Version 2.9
|
||||
Released: 2015-10-15
|
||||
|
||||
New
|
||||
* GZIP Encoding in updater
|
||||
* Adds --throttle option to throttle requests
|
||||
* Uses new API and local database file structure
|
||||
* Adds last updated and latest version to plugins and themes
|
||||
|
||||
Removed
|
||||
* ArchAssault from README
|
||||
* APIv1 local databases
|
||||
|
||||
General core
|
||||
* Update to Ruby 2.2.3
|
||||
* Use yajl-ruby as JSON parser
|
||||
* New dependancy for Ubuntu 14.04 (libgmp-dev)
|
||||
* Use Travis container based infra and caching
|
||||
|
||||
Fixed issues
|
||||
* Fix #835 - Readme requests to wp root dir
|
||||
* Fix #836 - Critical icon output twice when the site is not running WP
|
||||
* Fix #839 - Terminal-table dependency is broken
|
||||
* Fix #841 - error: undefined method `cells' for #<Array:0x000000029cc2f8>
|
||||
* Fix #852 - GZIP Encoding in updater
|
||||
* Fix #853 - APIv2 integration
|
||||
* Fix #858 - Detection FP
|
||||
* Fix #873 - false positive "site has Must Use Plugins"
|
||||
|
||||
WPScan Database Statistics:
|
||||
* Total vulnerable versions: 132
|
||||
* Total vulnerable plugins: 1170
|
||||
* Total vulnerable themes: 368
|
||||
* Total version vulnerabilities: 1476
|
||||
* Total plugin vulnerabilities: 1913
|
||||
* Total theme vulnerabilities: 450
|
||||
|
||||
## Version 2.8
|
||||
Released: 2015-06-22
|
||||
|
||||
New
|
||||
* Warn the user to update his DB files
|
||||
* Added last db update to --version option (see #815)
|
||||
* Add db checksum to verbose logging during update
|
||||
* Option to hide banner
|
||||
* Continue if user chooses not to update + db exists
|
||||
* Don't update if user chooses default + no DBs exist
|
||||
* Updates request timeout values to realistic ones (and in seconds)
|
||||
|
||||
Removed
|
||||
* Removed `Time.parse('2000-01-01')` expedient
|
||||
* Removed unnecessary 'return' and '()'
|
||||
* Removed debug output
|
||||
* Removed wpstools
|
||||
|
||||
General core
|
||||
* Update to Ruby 2.2.2
|
||||
* Switch to mitre
|
||||
* Install bundler gem README
|
||||
* Switch from gnutls to openssl
|
||||
|
||||
Fixed issues
|
||||
* Fix #789 - Add blackarch to readme
|
||||
* Fix #790 - Consider the target down after 30 requests timed out requests instead of 10
|
||||
* Fix #791 - Rogue character causing the scan of non-wordpress site to crash
|
||||
* Fix #792 - Adds the HttpError exception
|
||||
* Fix #795 - Remove GHOST warning
|
||||
* Fix #796 - Do not swallow exit code
|
||||
* Fix #797 - Increases the timeout values
|
||||
* Fix #801 - Forces UTF-8 encoding when enumerating usernames
|
||||
* Fix #803 - Increases default connect-timeout to 10s
|
||||
* Fix #804 - Updates the Theme detection pattern
|
||||
* Fix #816 - Ignores potential non version chars in theme version detection
|
||||
* Fix #819 - Removes potential spaces in robots.txt entries
|
||||
|
||||
WPScan Database Statistics:
|
||||
* Total vulnerable versions: 98
|
||||
* Total vulnerable plugins: 1076
|
||||
* Total vulnerable themes: 361
|
||||
* Total version vulnerabilities: 1104
|
||||
* Total plugin vulnerabilities: 1763
|
||||
* Total theme vulnerabilities: 443
|
||||
|
||||
## Version 2.7
|
||||
Released: 2015-03-16
|
||||
|
||||
New
|
||||
* Detects version in release date format
|
||||
* Copyrights updated
|
||||
* WP version detection from stylesheets
|
||||
* New license
|
||||
* Global HTTP request counter
|
||||
* Add security-protection plugin detection
|
||||
* Add GHOST warning if XMLRPC enabled
|
||||
* Update databases from wpvulndb.com
|
||||
* Enumerate usernames from WP <= 3.0 (thanks berotti3)
|
||||
|
||||
Removed
|
||||
* README.txt
|
||||
|
||||
General core
|
||||
* Update to Ruby 2.2.1
|
||||
* Update to Ruby 2.2.0
|
||||
* Add addressable gem
|
||||
* Update Typhoeus gem to 0.7.0
|
||||
* IDN support: encode non-ascii domain names (thanks dctabuyz)
|
||||
* Improve page hash calculation (thanks dctabuyz)
|
||||
* Version detection regex improved
|
||||
|
||||
Fixed issues
|
||||
* Fix #745 - Plugin version pattern in readme.txt file not detected
|
||||
* Fix #746 - Add a global counter for all active requests to server.
|
||||
* Fix #747 - Add 'security-protection' plugin to wp_login_protection module
|
||||
* Fix #753 - undefined method `round' for "10":String for request or connect timeouts
|
||||
* Fix #760 - typhoeus issue (infinite loop)
|
||||
|
||||
WPScan Database Statistics:
|
||||
* Total vulnerable versions: 89
|
||||
* Total vulnerable plugins: 953
|
||||
* Total vulnerable themes: 329
|
||||
* Total version vulnerabilities: 1070
|
||||
* Total plugin vulnerabilities: 1451
|
||||
* Total theme vulnerabilities: 378
|
||||
|
||||
## Version 2.6
|
||||
Released: 2014-12-19
|
||||
|
||||
New
|
||||
* Updates the readmes to reflect the new --usernames option
|
||||
* Improves plugin/theme version detection by looking at the "Version:"
|
||||
* Solution to avoid mandatory blank newline at the end of the wordlist
|
||||
* Add check for valid credentials
|
||||
* Add Sucuri sponsor to banner
|
||||
* Add protocol to sucuri url in banner
|
||||
* Add response code to proxy error output
|
||||
* Add a statement about mendatory newlines at the end of list
|
||||
* Give warning if default username 'admin' is still used
|
||||
* License amendment to make it more clear about value added usage
|
||||
|
||||
Removed
|
||||
* remove malwares
|
||||
* remove malware folder
|
||||
* Removes the theme version check from the readme, unrealistic scenario
|
||||
|
||||
General core
|
||||
* Update to Ruby 2.1.5 and travis
|
||||
* Prevent parent theme infinite loop
|
||||
* Fixes the progressbar being overriden by next brute forcing attempts
|
||||
|
||||
Fixed issues
|
||||
* Fix UTF-8 encode on security db file download
|
||||
* Fix #703 - Disable logging by default. Implement log option.
|
||||
* Fix #705 - Installation instructions for Ubuntu < 14.04 apparently incomplete
|
||||
* Fix #717 - Expand on readme.html finding output
|
||||
* Fix #716 - Adds the --version in the help
|
||||
* Fix #715 - Add new updating info to docs
|
||||
* Fix #727 - WpItems detection: Perform the passive check and filter only vulnerable results at the end if required
|
||||
* Fix #737 - Adds some readme files to check for plugin versions
|
||||
* Fix #739 - Adds the --usernames option
|
||||
|
||||
WPScan Database Statistics:
|
||||
* Total vulnerable versions: 88
|
||||
* Total vulnerable plugins: 901
|
||||
* Total vulnerable themes: 313
|
||||
* Total version vulnerabilities: 1050
|
||||
* Total plugin vulnerabilities: 1355
|
||||
* Total theme vulnerabilities: 349
|
||||
|
||||
## Version 2.5.1
|
||||
Released: 2014-09-29
|
||||
|
||||
6
CREDITS
6
CREDITS
@@ -1,12 +1,12 @@
|
||||
**CREDITS**
|
||||
|
||||
This file is to give credit to WPScan's contributors. If you feel your name should be in here, email ryandewhurst at gmail.
|
||||
This file is used to state the individual WPScan Team members (core developers) and give credit to WPScan's other contributors. If you feel your name should be in here email team@wpscan.org.
|
||||
|
||||
*WPScan Team*
|
||||
|
||||
Erwan.LR - @erwan_lr - (Project Developer)
|
||||
Christian Mehlmauer - @_FireFart_ - (Project Developer)
|
||||
Peter van der Laan - pvdl - (Vuln Hunter and Code Cleaner)
|
||||
Peter van der Laan - pvdl - (Project Developer)
|
||||
Ryan Dewhurst - @ethicalhack3r (Project Lead)
|
||||
|
||||
*Other Contributors*
|
||||
@@ -18,4 +18,4 @@ Callum Pember - Implemented proxy support - callumpember at gmail.com
|
||||
g0tmi1k - Additional timthumb checks + bug reports
|
||||
Melvin Lammerts - Reported a couple of fake vulnerabilities - melvin at 12k.nl
|
||||
Paolo Perego - @thesp0nge - Basic authentication
|
||||
Gianluca Brindisi - @gbrindisi - Project Developer
|
||||
Gianluca Brindisi - @gbrindisi - Ex Project Developer
|
||||
|
||||
11
Gemfile
11
Gemfile
@@ -1,14 +1,17 @@
|
||||
source 'https://rubygems.org'
|
||||
|
||||
gem 'typhoeus', '~>0.6.8'
|
||||
gem 'typhoeus', '~>0.8.0'
|
||||
gem 'nokogiri'
|
||||
gem 'json'
|
||||
gem 'terminal-table'
|
||||
gem 'addressable'
|
||||
gem 'yajl-ruby' # Better JSON parser regarding memory usage
|
||||
# TODO: update the below when terminal-table 1.5.3+ is released.
|
||||
# (and delete the Terminal module in lib/common/hacks.rb)
|
||||
gem 'terminal-table', '~>1.4.5'
|
||||
gem 'ruby-progressbar', '>=1.6.0'
|
||||
|
||||
group :test do
|
||||
gem 'webmock', '>=1.17.2'
|
||||
gem 'simplecov'
|
||||
gem 'rspec', '~>3.0'
|
||||
gem 'rspec', '>=3.3.0'
|
||||
gem 'rspec-its'
|
||||
end
|
||||
|
||||
74
LICENSE
74
LICENSE
@@ -1,20 +1,70 @@
|
||||
The WPScan software and its data (henceforth both referred to simply as "WPScan") is dual-licensed - copyright 2011-2014 The WPScan Team.
|
||||
WPScan Public Source License
|
||||
|
||||
Cases that include commercialization of WPScan require a commercial, non-free license. Otherwise, the system can be used under the terms of the GNU General Public License.
|
||||
The WPScan software (henceforth referred to simply as "WPScan") is dual-licensed - Copyright 2011-2015 WPScan Team.
|
||||
|
||||
Cases of commercialization are:
|
||||
Cases that include commercialization of WPScan require a commercial, non-free license. Otherwise, WPScan can be used without charge under the terms set out below.
|
||||
|
||||
- Using WPScan to provide commercial managed/Software-as-a-Service services.
|
||||
- Distributing WPScan as a commercial product or as part of one.
|
||||
1. Definitions
|
||||
|
||||
Cases which do not require a commercial license, and thus fall under the terms of GNU General Public License, include (but are not limited to):
|
||||
1.1 “License” means this document.
|
||||
1.2 “Contributor” means each individual or legal entity that creates, contributes to the creation of, or owns WPScan.
|
||||
1.3 “WPScan Team” means WPScan’s core developers, an updated list of whom can be found within the CREDITS file.
|
||||
|
||||
- Penetration testers (or penetration testing organizations) using WPScan as part of their assessment toolkit. So long as that does not conflict with the commercialization clause.
|
||||
- Using WPScan to test your own systems.
|
||||
- Any non-commercial use of WPScan.
|
||||
2. Commercialization
|
||||
|
||||
If you need to acquire a commercial license or are unsure about whether you need to acquire a commercial license, please get in touch, we will be happy to clarify things for you and work with you to accommodate your requirements.
|
||||
A commercial use is one intended for commercial advantage or monetary compensation.
|
||||
|
||||
wpscanteam at gmail.com
|
||||
Example cases of commercialization are:
|
||||
|
||||
You should have received a copy of the GNU General Public License along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
- Using WPScan to provide commercial managed/Software-as-a-Service services.
|
||||
- Distributing WPScan as a commercial product or as part of one.
|
||||
- Using WPScan as a value added service/product.
|
||||
|
||||
Example cases which do not require a commercial license, and thus fall under the terms set out below, include (but are not limited to):
|
||||
|
||||
- Penetration testers (or penetration testing organizations) using WPScan as part of their assessment toolkit.
|
||||
- Penetration Testing Linux Distributions including but not limited to Kali Linux, SamuraiWTF, BackBox Linux.
|
||||
- Using WPScan to test your own systems.
|
||||
- Any non-commercial use of WPScan.
|
||||
|
||||
If you need to purchase a commercial license or are unsure whether you need to purchase a commercial license contact us - team@wpscan.org.
|
||||
|
||||
We may grant commercial licenses at no monetary cost at our own discretion if the commercial usage is deemed by the WPScan Team to significantly benefit WPScan.
|
||||
|
||||
Free-use Terms and Conditions;
|
||||
|
||||
3. Redistribution
|
||||
|
||||
Redistribution is permitted under the following conditions:
|
||||
|
||||
- Unmodified License is provided with WPScan.
|
||||
- Unmodified Copyright notices are provided with WPScan.
|
||||
- Does not conflict with the commercialization clause.
|
||||
|
||||
4. Copying
|
||||
|
||||
Copying is permitted so long as it does not conflict with the Redistribution clause.
|
||||
|
||||
5. Modification
|
||||
|
||||
Modification is permitted so long as it does not conflict with the Redistribution clause.
|
||||
|
||||
6. Contributions
|
||||
|
||||
Any Contributions assume the Contributor grants the WPScan Team the unlimited, non-exclusive right to reuse, modify and relicense the Contributor's content.
|
||||
|
||||
7. Support
|
||||
|
||||
WPScan is provided under an AS-IS basis and without any support, updates or maintenance. Support, updates and maintenance may be given according to the sole discretion of the WPScan Team.
|
||||
|
||||
8. Disclaimer of Warranty
|
||||
|
||||
WPScan is provided under this License on an “as is” basis, without warranty of any kind, either expressed, implied, or statutory, including, without limitation, warranties that the WPScan is free of defects, merchantable, fit for a particular purpose or non-infringing.
|
||||
|
||||
9. Limitation of Liability
|
||||
|
||||
To the extent permitted under Law, WPScan is provided under an AS-IS basis. The WPScan Team shall never, and without any limit, be liable for any damage, cost, expense or any other payment incurred as a result of WPScan's actions, failure, bugs and/or any other interaction between WPScan and end-equipment, computers, other software or any 3rd party, end-equipment, computer or services.
|
||||
|
||||
10. Disclaimer
|
||||
|
||||
Running WPScan against websites without prior mutual consent may be illegal in your country. The WPScan Team accept no liability and are not responsible for any misuse or damage caused by WPScan.
|
||||
|
||||
285
README
285
README
@@ -1,285 +0,0 @@
|
||||
__________________________________________________
|
||||
__ _______ _____
|
||||
\ \ / / __ \ / ____|
|
||||
\ \ /\ / /| |__) | (___ ___ __ _ _ __
|
||||
\ \/ \/ / | ___/ \___ \ / __|/ _` | '_ \
|
||||
\ /\ / | | ____) | (__| (_| | | | |
|
||||
\/ \/ |_| |_____/ \___|\__,_|_| |_|
|
||||
__________________________________________________
|
||||
|
||||
==LICENSE==
|
||||
|
||||
The WPScan software and its data (henceforth both referred to simply as "WPScan") is dual-licensed - copyright 2011-2014 The WPScan Team.
|
||||
|
||||
Cases that include commercialization of WPScan require a commercial, non-free license. Otherwise, the system can be used under the terms of the GNU General Public License.
|
||||
|
||||
Cases of commercialization are:
|
||||
|
||||
- Using WPScan to provide commercial managed/Software-as-a-Service services.
|
||||
- Distributing WPScan as a commercial product or as part of one.
|
||||
|
||||
Cases which do not require a commercial license, and thus fall under the terms of GNU General Public License, include (but are not limited to):
|
||||
|
||||
- Penetration testers (or penetration testing organizations) using WPScan as part of their assessment toolkit. So long as that does not conflict with the commercialization clause.
|
||||
- Using WPScan to test your own systems.
|
||||
- Any non-commercial use of WPScan.
|
||||
|
||||
If you need to acquire a commercial license or are unsure about whether you need to acquire a commercial license, please get in touch, we will be happy to clarify things for you and work with you to accommodate your requirements.
|
||||
|
||||
wpscanteam at gmail.com
|
||||
|
||||
You should have received a copy of the GNU General Public License along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
==INSTALL==
|
||||
|
||||
WPScan comes pre-installed on the following Linux distributions:
|
||||
|
||||
* BackBox Linux
|
||||
* Kali Linux
|
||||
* Pentoo
|
||||
* SamuraiWTF
|
||||
* ArchAssault
|
||||
|
||||
Prerequisites:
|
||||
|
||||
* Windows not supported
|
||||
* Ruby >= 1.9.2 - Recommended: 2.1.2
|
||||
* Curl >= 7.21 - Recommended: latest - FYI the 7.29 has a segfault
|
||||
* RubyGems - Recommended: latest
|
||||
* Git
|
||||
|
||||
-> Installing on Ubuntu:
|
||||
|
||||
Before Ubuntu 14.04:
|
||||
|
||||
sudo apt-get install libcurl4-gnutls-dev libopenssl-ruby libxml2 libxml2-dev libxslt1-dev ruby-dev
|
||||
|
||||
From Ubuntu 14.04:
|
||||
|
||||
sudo apt-get install libcurl4-gnutls-dev libxml2 libxml2-dev libxslt1-dev ruby-dev build-essential
|
||||
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler && bundle install --without test
|
||||
|
||||
-> Installing on Debian:
|
||||
|
||||
sudo apt-get install git ruby ruby-dev libcurl4-gnutls-dev make
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler
|
||||
bundle install --without test --path vendor/bundle
|
||||
|
||||
-> Installing on Fedora:
|
||||
|
||||
sudo yum install gcc ruby-devel libxml2 libxml2-devel libxslt libxslt-devel libcurl-devel
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler && bundle install --without test
|
||||
|
||||
-> Installing on Archlinux:
|
||||
|
||||
pacman -Syu ruby
|
||||
pacman -Syu libyaml
|
||||
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler && bundle install --without test
|
||||
|
||||
gem install typhoeus
|
||||
gem install nokogiri
|
||||
|
||||
-> Installing on Mac OS X:
|
||||
|
||||
Apple Xcode, Command Line Tools and the libffi are needed (to be able to install the FFI gem), See http://stackoverflow.com/questions/17775115/cant-setup-ruby-environment-installing-fii-gem-error
|
||||
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler && sudo bundle install --without test
|
||||
|
||||
-> Installing with RVM:
|
||||
|
||||
cd ~
|
||||
curl -sSL https://get.rvm.io | bash -s stable
|
||||
source ~/.rvm/scripts/rvm
|
||||
echo "source ~/.rvm/scripts/rvm" >> ~/.bashrc
|
||||
rvm install 2.1.2
|
||||
rvm use 2.1.2 --default
|
||||
echo "gem: --no-ri --no-rdoc" > ~/.gemrc
|
||||
gem install bundler
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
bundle install --without test
|
||||
|
||||
==KNOWN ISSUES==
|
||||
|
||||
- Typhoeus segmentation fault:
|
||||
Update cURL to version => 7.21 (may have to install from source)
|
||||
|
||||
- Proxy not working:
|
||||
Update cURL to version => 7.21.7 (may have to install from source).
|
||||
|
||||
Installation from sources :
|
||||
- Grab the sources from http://curl.haxx.se/download.html
|
||||
- Decompress the archive
|
||||
- Open the folder with the extracted files
|
||||
- Run ./configure
|
||||
- Run make
|
||||
- Run sudo make install
|
||||
- Run sudo ldconfig
|
||||
|
||||
- cannot load such file -- readline:
|
||||
Run sudo aptitude install libreadline5-dev libncurses5-dev
|
||||
|
||||
Then, open the directory of the readline gem (you have to locate it)
|
||||
|
||||
cd ~/.rvm/src/ruby-1.9.2-p180/ext/readline
|
||||
ruby extconf.rb
|
||||
make
|
||||
make install
|
||||
|
||||
See http://vvv.tobiassjosten.net/ruby-on-rails/fixing-readline-for-the-ruby-on-rails-console/ for more details
|
||||
|
||||
- no such file to load -- rubygems
|
||||
Run update-alternatives --config ruby
|
||||
And select your ruby version
|
||||
|
||||
See https://github.com/wpscanteam/wpscan/issues/148
|
||||
|
||||
|
||||
==WPSCAN ARGUMENTS==
|
||||
|
||||
--update Update the databases.
|
||||
|
||||
--url | -u <target url> The WordPress URL/domain to scan.
|
||||
|
||||
--force | -f Forces WPScan to not check if the remote site is running WordPress.
|
||||
|
||||
--enumerate | -e [option(s)] Enumeration.
|
||||
option :
|
||||
u usernames from id 1 to 10
|
||||
u[10-20] usernames from id 10 to 20 (you must write [] chars)
|
||||
p plugins
|
||||
vp only vulnerable plugins
|
||||
ap all plugins (can take a long time)
|
||||
tt timthumbs
|
||||
t themes
|
||||
vt only vulnerable themes
|
||||
at all themes (can take a long time)
|
||||
Multiple values are allowed : "-e tt,p" will enumerate timthumbs and plugins
|
||||
If no option is supplied, the default is "vt,tt,u,vp"
|
||||
|
||||
--exclude-content-based "<regexp or string>" Used with the enumeration option, will exclude all occurrences based on the regexp or string supplied
|
||||
You do not need to provide the regexp delimiters, but you must write the quotes (simple or double)
|
||||
|
||||
--config-file | -c <config file> Use the specified config file, see the example.conf.json
|
||||
|
||||
--user-agent | -a <User-Agent> Use the specified User-Agent
|
||||
|
||||
--random-agent | -r Use a random User-Agent
|
||||
|
||||
--follow-redirection If the target url has a redirection, it will be followed without asking if you wanted to do so or not
|
||||
|
||||
--wp-content-dir <wp content dir> WPScan try to find the content directory (ie wp-content) by scanning the index page, however you can specified it. Subdirectories are allowed
|
||||
|
||||
--wp-plugins-dir <wp plugins dir> Same thing than --wp-content-dir but for the plugins directory. If not supplied, WPScan will use wp-content-dir/plugins. Subdirectories are allowed
|
||||
|
||||
--proxy <[protocol://]host:port> Supply a proxy (will override the one from conf/browser.conf.json).
|
||||
HTTP, SOCKS4 SOCKS4A and SOCKS5 are supported. If no protocol is given (format host:port), HTTP will be used
|
||||
|
||||
--proxy-auth <username:password> Supply the proxy login credentials.
|
||||
|
||||
--basic-auth <username:password> Set the HTTP Basic authentication.
|
||||
|
||||
--wordlist | -w <wordlist> Supply a wordlist for the password bruter and do the brute.
|
||||
|
||||
--threads | -t <number of threads> The number of threads to use when multi-threading requests.
|
||||
|
||||
--username | -U <username> Only brute force the supplied username.
|
||||
|
||||
--cache-ttl <cache-ttl> Typhoeus cache TTL.
|
||||
|
||||
--request-timeout <request-timeout> Request Timeout.
|
||||
|
||||
--connect-timeout <connect-timeout> Connect Timeout.
|
||||
|
||||
--max-threads <max-threads> Maximum Threads.
|
||||
|
||||
--help | -h This help screen.
|
||||
|
||||
--verbose | -v Verbose output.
|
||||
|
||||
--batch Never ask for user input, use the default behaviour.
|
||||
|
||||
--no-color Do not use colors in the output.
|
||||
|
||||
==WPSCAN EXAMPLES==
|
||||
|
||||
Do 'non-intrusive' checks...
|
||||
|
||||
ruby wpscan.rb --url www.example.com
|
||||
|
||||
Do wordlist password brute force on enumerated users using 50 threads...
|
||||
|
||||
ruby wpscan.rb --url www.example.com --wordlist darkc0de.lst --threads 50
|
||||
|
||||
Do wordlist password brute force on the 'admin' username only...
|
||||
|
||||
ruby wpscan.rb --url www.example.com --wordlist darkc0de.lst --username admin
|
||||
|
||||
Enumerate installed plugins...
|
||||
|
||||
ruby wpscan.rb --url www.example.com --enumerate p
|
||||
|
||||
Run all enumeration tools...
|
||||
|
||||
ruby wpscan.rb --url www.example.com --enumerate
|
||||
|
||||
Use custom content directory...
|
||||
|
||||
ruby wpscan.rb -u www.example.com --wp-content-dir custom-content
|
||||
|
||||
Update WPScan's databases...
|
||||
|
||||
ruby wpscan.rb --update
|
||||
|
||||
Debug output...
|
||||
|
||||
ruby wpscan.rb --url www.example.com --debug-output 2>debug.log
|
||||
|
||||
==WPSTOOLS ARGUMENTS==
|
||||
|
||||
-v, --verbose Verbose output
|
||||
--check-vuln-ref-urls, --cvru Check all the vulnerabilities reference urls for 404
|
||||
--check-local-vulnerable-files, --clvf LOCAL_DIRECTORY Perform a recursive scan in the LOCAL_DIRECTORY to find vulnerable files or shells
|
||||
s, --stats Show WpScan Database statistics.
|
||||
--spellcheck, --sc Check all files for common spelling mistakes.
|
||||
|
||||
==WPSTOOLS EXAMPLES==
|
||||
|
||||
Locally scan a wordpress installation for vulnerable files or shells:
|
||||
ruby wpstools.rb --check-local-vulnerable-files /var/www/wordpress/
|
||||
|
||||
Or check https://github.com/fgeek/pyfiscan project.
|
||||
|
||||
===PROJECT HOME===
|
||||
|
||||
www.wpscan.org
|
||||
|
||||
===REPOSITORY===
|
||||
|
||||
https://github.com/wpscanteam/wpscan
|
||||
|
||||
===ISSUES===
|
||||
|
||||
https://github.com/wpscanteam/wpscan/issues
|
||||
|
||||
===DEVELOPER DOCUMENTATION===
|
||||
|
||||
http://rdoc.info/github/wpscanteam/wpscan/frames
|
||||
|
||||
===SPONSOR===
|
||||
|
||||
WPScan is sponsored by the RandomStorm Open Source Initiative.
|
||||
|
||||
Visit RandomStorm at http://www.randomstorm.com
|
||||
141
README.md
141
README.md
@@ -1,29 +1,84 @@
|
||||

|
||||
|
||||
[](https://travis-ci.org/wpscanteam/wpscan)
|
||||
|
||||
[](https://travis-ci.org/wpscanteam/wpscan)
|
||||
[](https://codeclimate.com/github/wpscanteam/wpscan)
|
||||
[](https://gemnasium.com/wpscanteam/wpscan)
|
||||
|
||||
#### LICENSE
|
||||
|
||||
The WPScan software and its data (henceforth both referred to simply as "WPScan") is dual-licensed - copyright 2011-2014 The WPScan Team.
|
||||
#### WPScan Public Source License
|
||||
|
||||
Cases that include commercialization of WPScan require a commercial, non-free license. Otherwise, the system can be used under the terms of the GNU General Public License.
|
||||
The WPScan software (henceforth referred to simply as "WPScan") is dual-licensed - Copyright 2011-2015 WPScan Team.
|
||||
|
||||
Cases of commercialization are:
|
||||
Cases that include commercialization of WPScan require a commercial, non-free license. Otherwise, WPScan can be used without charge under the terms set out below.
|
||||
|
||||
- Using WPScan to provide commercial managed/Software-as-a-Service services.
|
||||
- Distributing WPScan as a commercial product or as part of one.
|
||||
##### 1. Definitions
|
||||
|
||||
Cases which do not require a commercial license, and thus fall under the terms of GNU General Public License, include (but are not limited to):
|
||||
1.1 "License" means this document.
|
||||
|
||||
- Penetration testers (or penetration testing organizations) using WPScan as part of their assessment toolkit. So long as that does not conflict with the commercialization clause.
|
||||
- Using WPScan to test your own systems.
|
||||
- Any non-commercial use of WPScan.
|
||||
1.2 "Contributor" means each individual or legal entity that creates, contributes to the creation of, or owns WPScan.
|
||||
|
||||
If you need to acquire a commercial license or are unsure about whether you need to acquire a commercial license, please get in touch, we will be happy to clarify things for you and work with you to accommodate your requirements.
|
||||
1.3 "WPScan Team" means WPScan’s core developers, an updated list of whom can be found within the CREDITS file.
|
||||
|
||||
wpscanteam at gmail.com
|
||||
##### 2. Commercialization
|
||||
|
||||
You should have received a copy of the GNU General Public License along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
A commercial use is one intended for commercial advantage or monetary compensation.
|
||||
|
||||
Example cases of commercialization are:
|
||||
|
||||
- Using WPScan to provide commercial managed/Software-as-a-Service services.
|
||||
- Distributing WPScan as a commercial product or as part of one.
|
||||
- Using WPScan as a value added service/product.
|
||||
|
||||
Example cases which do not require a commercial license, and thus fall under the terms set out below, include (but are not limited to):
|
||||
|
||||
- Penetration testers (or penetration testing organizations) using WPScan as part of their assessment toolkit.
|
||||
- Penetration Testing Linux Distributions including but not limited to Kali Linux, SamuraiWTF, BackBox Linux.
|
||||
- Using WPScan to test your own systems.
|
||||
- Any non-commercial use of WPScan.
|
||||
|
||||
If you need to purchase a commercial license or are unsure whether you need to purchase a commercial license contact us - team@wpscan.org.
|
||||
|
||||
We may grant commercial licenses at no monetary cost at our own discretion if the commercial usage is deemed by the WPScan Team to significantly benefit WPScan.
|
||||
|
||||
Free-use Terms and Conditions;
|
||||
|
||||
##### 3. Redistribution
|
||||
|
||||
Redistribution is permitted under the following conditions:
|
||||
|
||||
- Unmodified License is provided with WPScan.
|
||||
- Unmodified Copyright notices are provided with WPScan.
|
||||
- Does not conflict with the commercialization clause.
|
||||
|
||||
##### 4. Copying
|
||||
|
||||
Copying is permitted so long as it does not conflict with the Redistribution clause.
|
||||
|
||||
##### 5. Modification
|
||||
|
||||
Modification is permitted so long as it does not conflict with the Redistribution clause.
|
||||
|
||||
##### 6. Contributions
|
||||
|
||||
Any Contributions assume the Contributor grants the WPScan Team the unlimited, non-exclusive right to reuse, modify and relicense the Contributor's content.
|
||||
|
||||
##### 7. Support
|
||||
|
||||
WPScan is provided under an AS-IS basis and without any support, updates or maintenance. Support, updates and maintenance may be given according to the sole discretion of the WPScan Team.
|
||||
|
||||
##### 8. Disclaimer of Warranty
|
||||
|
||||
WPScan is provided under this License on an “as is” basis, without warranty of any kind, either expressed, implied, or statutory, including, without limitation, warranties that the WPScan is free of defects, merchantable, fit for a particular purpose or non-infringing.
|
||||
|
||||
##### 9. Limitation of Liability
|
||||
|
||||
To the extent permitted under Law, WPScan is provided under an AS-IS basis. The WPScan Team shall never, and without any limit, be liable for any damage, cost, expense or any other payment incurred as a result of WPScan's actions, failure, bugs and/or any other interaction between WPScan and end-equipment, computers, other software or any 3rd party, end-equipment, computer or services.
|
||||
|
||||
##### 10. Disclaimer
|
||||
|
||||
Running WPScan against websites without prior mutual consent may be illegal in your country. The WPScan Team accept no liability and are not responsible for any misuse or damage caused by WPScan.
|
||||
|
||||
#### INSTALL
|
||||
|
||||
@@ -33,33 +88,37 @@ WPScan comes pre-installed on the following Linux distributions:
|
||||
- [Kali Linux](http://www.kali.org/)
|
||||
- [Pentoo](http://www.pentoo.ch/)
|
||||
- [SamuraiWTF](http://samurai.inguardians.com/)
|
||||
- [ArchAssault](https://archassault.org/)
|
||||
- [BlackArch](http://blackarch.org/)
|
||||
|
||||
Prerequisites:
|
||||
|
||||
- Ruby >= 1.9.2 - Recommended: 2.1.2
|
||||
- Ruby >= 1.9.2 - Recommended: 2.2.3
|
||||
- Curl >= 7.21 - Recommended: latest - FYI the 7.29 has a segfault
|
||||
- RubyGems - Recommended: latest
|
||||
- Git
|
||||
|
||||
Windows is not supported.
|
||||
If installed from Github update the code base with ```git pull```. The databases are updated with ```wpscan.rb --update```.
|
||||
|
||||
####Installing on Ubuntu:
|
||||
|
||||
Before Ubuntu 14.04:
|
||||
|
||||
sudo apt-get install libcurl4-gnutls-dev libopenssl-ruby libxml2 libxml2-dev libxslt1-dev ruby-dev
|
||||
sudo apt-get install libcurl4-openssl-dev libopenssl-ruby libxml2 libxml2-dev libxslt1-dev ruby-dev
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler && bundle install --without test
|
||||
|
||||
From Ubuntu 14.04:
|
||||
|
||||
sudo apt-get install libcurl4-gnutls-dev libxml2 libxml2-dev libxslt1-dev ruby-dev build-essential
|
||||
sudo apt-get install libcurl4-openssl-dev libxml2 libxml2-dev libxslt1-dev ruby-dev build-essential libgmp-dev
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler && bundle install --without test
|
||||
|
||||
####Installing on Debian:
|
||||
|
||||
sudo apt-get install git ruby ruby-dev libcurl4-gnutls-dev make
|
||||
sudo apt-get install git ruby ruby-dev libcurl4-openssl-dev make
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler
|
||||
@@ -67,7 +126,7 @@ From Ubuntu 14.04:
|
||||
|
||||
####Installing on Fedora:
|
||||
|
||||
sudo yum install gcc ruby-devel libxml2 libxml2-devel libxslt libxslt-devel libcurl-devel
|
||||
sudo yum install gcc ruby-devel libxml2 libxml2-devel libxslt libxslt-devel libcurl-devel patch
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
sudo gem install bundler && bundle install --without test
|
||||
@@ -96,12 +155,13 @@ Apple Xcode, Command Line Tools and the libffi are needed (to be able to install
|
||||
curl -sSL https://get.rvm.io | bash -s stable
|
||||
source ~/.rvm/scripts/rvm
|
||||
echo "source ~/.rvm/scripts/rvm" >> ~/.bashrc
|
||||
rvm install 2.1.2
|
||||
rvm use 2.1.2 --default
|
||||
rvm install 2.2.3
|
||||
rvm use 2.2.3 --default
|
||||
echo "gem: --no-ri --no-rdoc" > ~/.gemrc
|
||||
gem install bundler
|
||||
git clone https://github.com/wpscanteam/wpscan.git
|
||||
cd wpscan
|
||||
gem install bundler
|
||||
bundle install --without test
|
||||
|
||||
#### KNOWN ISSUES
|
||||
@@ -115,7 +175,7 @@ Apple Xcode, Command Line Tools and the libffi are needed (to be able to install
|
||||
Update cURL to version => 7.21.7 (may have to install from source).
|
||||
|
||||
Installation from sources :
|
||||
|
||||
|
||||
Grab the sources from http://curl.haxx.se/download.html
|
||||
Decompress the archive
|
||||
Open the folder with the extracted files
|
||||
@@ -123,19 +183,19 @@ Apple Xcode, Command Line Tools and the libffi are needed (to be able to install
|
||||
Run make
|
||||
Run sudo make install
|
||||
Run sudo ldconfig
|
||||
|
||||
|
||||
|
||||
- cannot load such file -- readline:
|
||||
|
||||
sudo aptitude install libreadline5-dev libncurses5-dev
|
||||
|
||||
Then, open the directory of the readline gem (you have to locate it)
|
||||
|
||||
|
||||
cd ~/.rvm/src/ruby-1.9.2-p180/ext/readline
|
||||
ruby extconf.rb
|
||||
make
|
||||
make install
|
||||
|
||||
|
||||
|
||||
See [http://vvv.tobiassjosten.net/ruby-on-rails/fixing-readline-for-the-ruby-on-rails-console/](http://vvv.tobiassjosten.net/ruby-on-rails/fixing-readline-for-the-ruby-on-rails-console/) for more details
|
||||
|
||||
@@ -191,12 +251,14 @@ Apple Xcode, Command Line Tools and the libffi are needed (to be able to install
|
||||
|
||||
--basic-auth <username:password> Set the HTTP Basic authentication.
|
||||
|
||||
--wordlist | -w <wordlist> Supply a wordlist for the password bruter and do the brute.
|
||||
--wordlist | -w <wordlist> Supply a wordlist for the password brute forcer.
|
||||
|
||||
--threads | -t <number of threads> The number of threads to use when multi-threading requests.
|
||||
|
||||
--username | -U <username> Only brute force the supplied username.
|
||||
|
||||
--usernames <path-to-file> Only brute force the usernames from the file.
|
||||
|
||||
--cache-ttl <cache-ttl> Typhoeus cache TTL.
|
||||
|
||||
--request-timeout <request-timeout> Request Timeout.
|
||||
@@ -209,10 +271,12 @@ Apple Xcode, Command Line Tools and the libffi are needed (to be able to install
|
||||
|
||||
--verbose | -v Verbose output.
|
||||
|
||||
--batch Never ask for user input, use the default behaviour.
|
||||
--batch Never ask for user input, use the default behavior.
|
||||
|
||||
--no-color Do not use colors in the output.
|
||||
|
||||
--log Save STDOUT to log.txt
|
||||
|
||||
#### WPSCAN EXAMPLES
|
||||
|
||||
Do 'non-intrusive' checks...
|
||||
@@ -247,30 +311,13 @@ Debug output...
|
||||
|
||||
```ruby wpscan.rb --url www.example.com --debug-output 2>debug.log```
|
||||
|
||||
#### WPSTOOLS ARGUMENTS
|
||||
|
||||
-v, --verbose Verbose output
|
||||
--check-vuln-ref-urls, --cvru Check all the vulnerabilities reference urls for 404
|
||||
--check-local-vulnerable-files, --clvf LOCAL_DIRECTORY Perform a recursive scan in the LOCAL_DIRECTORY to find vulnerable files or shells
|
||||
-s, --stats Show WpScan Database statistics.
|
||||
--spellcheck, --sc Check all files for common spelling mistakes.
|
||||
|
||||
|
||||
#### WPSTOOLS EXAMPLES
|
||||
|
||||
Locally scan a wordpress installation for vulnerable files or shells:
|
||||
|
||||
```ruby wpstools.rb --check-local-vulnerable-files /var/www/wordpress/```
|
||||
|
||||
Or check [pyfiscan](https://github.com/fgeek/pyfiscan) project.
|
||||
|
||||
#### PROJECT HOME
|
||||
|
||||
[http://www.wpscan.org](http://www.wpscan.org)
|
||||
|
||||
#### VULNERABILITY DATABASE
|
||||
|
||||
[https://www.wpvulndb.com](https://www.wpvulndb.com)
|
||||
[https://wpvulndb.com](https://wpvulndb.com)
|
||||
|
||||
#### GIT REPOSITORY
|
||||
|
||||
@@ -284,6 +331,6 @@ Or check [pyfiscan](https://github.com/fgeek/pyfiscan) project.
|
||||
|
||||
[http://rdoc.info/github/wpscanteam/wpscan/frames](http://rdoc.info/github/wpscanteam/wpscan/frames)
|
||||
|
||||
#### SPONSOR
|
||||
#### SPECIAL THANKS
|
||||
|
||||
WPScan is sponsored by the [RandomStorm](http://www.randomstorm.com) Open Source Initiative.
|
||||
[RandomStorm](https://www.randomstorm.com)
|
||||
|
||||
@@ -23,7 +23,7 @@ end
|
||||
html = open(html_path).read
|
||||
examples = html.match(/(\d+) examples/)[0].to_i rescue 0
|
||||
errors = html.match(/(\d+) errors/)[0].to_i rescue 0
|
||||
if errors == 0 then
|
||||
if errors == 0
|
||||
errors = html.match(/(\d+) failure/)[0].to_i rescue 0
|
||||
end
|
||||
pending = html.match(/(\d+) pending/)[0].to_i rescue 0
|
||||
|
||||
@@ -10,9 +10,9 @@
|
||||
|
||||
"cache_ttl": 600, // 10 minutes, at this time the cache is cleaned before each scan. If this value is set to 0, the cache will be disabled
|
||||
|
||||
"request_timeout": 2000, // 2s
|
||||
"request_timeout": 60, // 1min
|
||||
|
||||
"connect_timeout": 1000, // 1s
|
||||
"connect_timeout": 10, // 10s
|
||||
|
||||
"max_threads": 20
|
||||
}
|
||||
|
||||
@@ -17,20 +17,21 @@ class Browser
|
||||
:proxy_auth,
|
||||
:request_timeout,
|
||||
:connect_timeout,
|
||||
:cookie
|
||||
:cookie,
|
||||
:throttle
|
||||
]
|
||||
|
||||
@@instance = nil
|
||||
|
||||
attr_reader :hydra, :cache_dir
|
||||
|
||||
attr_accessor :referer, :cookie
|
||||
attr_accessor :referer, :cookie, :vhost
|
||||
|
||||
# @param [ Hash ] options
|
||||
#
|
||||
# @return [ Browser ]
|
||||
def initialize(options = {})
|
||||
@cache_dir = options[:cache_dir] || CACHE_DIR + '/browser'
|
||||
@cache_dir = options[:cache_dir] || CACHE_DIR + '/browser'
|
||||
|
||||
# sets browser defaults
|
||||
browser_defaults
|
||||
@@ -70,14 +71,14 @@ class Browser
|
||||
# sets browser default values
|
||||
#
|
||||
def browser_defaults
|
||||
@max_threads = 20
|
||||
# 10 minutes, at this time the cache is cleaned before each scan. If this value is set to 0, the cache will be disabled
|
||||
@cache_ttl = 600
|
||||
# 2s
|
||||
@request_timeout = 2000
|
||||
# 1s
|
||||
@connect_timeout = 1000
|
||||
@user_agent = "WPScan v#{WPSCAN_VERSION} (http://wpscan.org)"
|
||||
@max_threads = 20
|
||||
# 10 minutes, at this time the cache is cleaned before each scan.
|
||||
# If this value is set to 0, the cache will be disabled
|
||||
@cache_ttl = 600
|
||||
@request_timeout = 60 # 60s
|
||||
@connect_timeout = 10 # 10s
|
||||
@user_agent = "WPScan v#{WPSCAN_VERSION} (http://wpscan.org)"
|
||||
@throttle = 0
|
||||
end
|
||||
|
||||
#
|
||||
@@ -88,7 +89,6 @@ class Browser
|
||||
#
|
||||
# @return [ void ]
|
||||
def load_config(config_file = nil)
|
||||
|
||||
if File.symlink?(config_file)
|
||||
raise '[ERROR] Config file is a symlink.'
|
||||
else
|
||||
@@ -101,7 +101,6 @@ class Browser
|
||||
self.send(:"#{option_name}=", data[option_name])
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
# @param [ String ] url
|
||||
@@ -123,11 +122,8 @@ class Browser
|
||||
)
|
||||
|
||||
if @proxy
|
||||
params = params.merge(proxy: @proxy)
|
||||
|
||||
if @proxy_auth
|
||||
params = params.merge(proxyauth: @proxy_auth)
|
||||
end
|
||||
params.merge!(proxy: @proxy)
|
||||
params.merge!(proxyauth: @proxy_auth) if @proxy_auth
|
||||
end
|
||||
|
||||
if @basic_auth
|
||||
@@ -138,15 +134,23 @@ class Browser
|
||||
)
|
||||
end
|
||||
|
||||
if vhost
|
||||
params = Browser.append_params_header_field(
|
||||
params,
|
||||
'Host',
|
||||
vhost
|
||||
)
|
||||
end
|
||||
|
||||
params.merge!(referer: referer)
|
||||
params.merge!(timeout: @request_timeout) if @request_timeout
|
||||
params.merge!(connecttimeout: @connect_timeout) if @connect_timeout
|
||||
|
||||
# Used to enable the cache system if :cache_ttl > 0
|
||||
params.merge!(cache_ttl: @cache_ttl) unless params.has_key?(:cache_ttl)
|
||||
params.merge!(cache_ttl: @cache_ttl) unless params.key?(:cache_ttl)
|
||||
|
||||
# Prevent infinite self redirection
|
||||
params.merge!(maxredirs: 3) unless params.has_key?(:maxredirs)
|
||||
params.merge!(maxredirs: 3) unless params.key?(:maxredirs)
|
||||
|
||||
# Disable SSL-Certificate checks
|
||||
params.merge!(ssl_verifypeer: false)
|
||||
@@ -174,5 +178,4 @@ class Browser
|
||||
end
|
||||
params
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
@@ -4,7 +4,7 @@ class Browser
|
||||
module Options
|
||||
|
||||
attr_accessor :cache_ttl, :request_timeout, :connect_timeout
|
||||
attr_reader :basic_auth, :proxy, :proxy_auth
|
||||
attr_reader :basic_auth, :proxy, :proxy_auth, :throttle
|
||||
attr_writer :user_agent
|
||||
|
||||
# Sets the Basic Authentification credentials
|
||||
@@ -82,7 +82,7 @@ class Browser
|
||||
#
|
||||
# @return [ void ]
|
||||
def request_timeout=(timeout)
|
||||
@request_timeout = timeout
|
||||
@request_timeout = timeout.to_i
|
||||
end
|
||||
|
||||
# Sets the connect timeout
|
||||
@@ -90,7 +90,12 @@ class Browser
|
||||
#
|
||||
# @return [ void ]
|
||||
def connect_timeout=(timeout)
|
||||
@connect_timeout = timeout
|
||||
@connect_timeout = timeout.to_i
|
||||
end
|
||||
|
||||
# @param [ String, Integer ] throttle
|
||||
def throttle=(throttle)
|
||||
@throttle = throttle.to_i.abs / 1000.0
|
||||
end
|
||||
|
||||
protected
|
||||
@@ -110,6 +115,5 @@ class Browser
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
@@ -9,15 +9,17 @@
|
||||
#
|
||||
|
||||
require 'yaml'
|
||||
require 'fileutils'
|
||||
|
||||
class CacheFileStore
|
||||
attr_reader :storage_path, :serializer
|
||||
attr_reader :storage_path, :cache_dir, :serializer
|
||||
|
||||
# The serializer must have the 2 methods .load and .dump
|
||||
# (Marshal and YAML have them)
|
||||
# YAML is Human Readable, contrary to Marshal which store in a binary format
|
||||
# Marshal does not need any "require"
|
||||
def initialize(storage_path, serializer = Marshal)
|
||||
@cache_dir = File.expand_path(storage_path)
|
||||
@storage_path = File.expand_path(File.join(storage_path, storage_dir))
|
||||
@serializer = serializer
|
||||
|
||||
@@ -29,15 +31,23 @@ class CacheFileStore
|
||||
end
|
||||
|
||||
def clean
|
||||
Dir[File.join(@storage_path, '*')].each do |f|
|
||||
File.delete(f) unless File.symlink?(f)
|
||||
# clean old directories
|
||||
Dir[File.join(@cache_dir, '*')].each do |f|
|
||||
if File.directory?(f)
|
||||
# delete directory if create time is older than 4 hours
|
||||
FileUtils.rm_rf(f) if File.mtime(f) < (Time.now - (60*240))
|
||||
else
|
||||
File.delete(f) unless File.symlink?(f)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def read_entry(key)
|
||||
@serializer.load(File.read(get_entry_file_path(key)))
|
||||
rescue
|
||||
nil
|
||||
begin
|
||||
@serializer.load(File.read(get_entry_file_path(key)))
|
||||
rescue
|
||||
nil
|
||||
end
|
||||
end
|
||||
|
||||
def write_entry(key, data_to_store, cache_ttl)
|
||||
|
||||
@@ -1,74 +1,75 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
require 'common/collections/wp_items/detectable'
|
||||
require 'common/collections/wp_items/output'
|
||||
|
||||
class WpItems < Array
|
||||
extend WpItems::Detectable
|
||||
include WpItems::Output
|
||||
|
||||
attr_accessor :wp_target
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
def initialize(wp_target = nil)
|
||||
self.wp_target = wp_target
|
||||
end
|
||||
|
||||
# @param [String,] argv
|
||||
#
|
||||
# @return [ void ]
|
||||
def add(*args)
|
||||
index = 0
|
||||
|
||||
until args[index].nil?
|
||||
arg = args[index]
|
||||
|
||||
if arg.is_a?(String)
|
||||
if (next_arg = args[index + 1]).is_a?(Hash)
|
||||
item = create_item(arg, next_arg)
|
||||
index += 1
|
||||
else
|
||||
item = create_item(arg)
|
||||
end
|
||||
elsif arg.is_a?(Item)
|
||||
item = arg
|
||||
else
|
||||
raise 'Invalid arguments'
|
||||
end
|
||||
|
||||
self << item
|
||||
index += 1
|
||||
end
|
||||
end
|
||||
|
||||
# @param [ String ] name
|
||||
# @param [ Hash ] attrs
|
||||
#
|
||||
# @return [ WpItem ]
|
||||
def create_item(name, attrs = {})
|
||||
raise 'wp_target must be set' unless wp_target
|
||||
|
||||
item_class.new(
|
||||
wp_target.uri,
|
||||
attrs.merge(
|
||||
name: name,
|
||||
wp_content_dir: wp_target.wp_content_dir,
|
||||
wp_plugins_dir: wp_target.wp_plugins_dir
|
||||
) { |key, oldval, newval| oldval }
|
||||
)
|
||||
end
|
||||
|
||||
# @param [ WpItems ] other
|
||||
#
|
||||
# @return [ self ]
|
||||
def +(other)
|
||||
other.each { |item| self << item }
|
||||
self
|
||||
end
|
||||
|
||||
protected
|
||||
# @return [ Class ]
|
||||
def item_class
|
||||
Object.const_get(self.class.to_s.gsub(/.$/, ''))
|
||||
end
|
||||
end
|
||||
# encoding: UTF-8
|
||||
|
||||
require 'common/collections/wp_items/detectable'
|
||||
require 'common/collections/wp_items/output'
|
||||
|
||||
class WpItems < Array
|
||||
extend WpItems::Detectable
|
||||
include WpItems::Output
|
||||
|
||||
attr_accessor :wp_target
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
def initialize(wp_target = nil)
|
||||
self.wp_target = wp_target
|
||||
end
|
||||
|
||||
# @param [String] args
|
||||
#
|
||||
# @return [ void ]
|
||||
def add(*args)
|
||||
index = 0
|
||||
|
||||
until args[index].nil?
|
||||
arg = args[index]
|
||||
|
||||
if arg.is_a?(String)
|
||||
if (next_arg = args[index + 1]).is_a?(Hash)
|
||||
item = create_item(arg, next_arg)
|
||||
index += 1
|
||||
else
|
||||
item = create_item(arg)
|
||||
end
|
||||
elsif arg.is_a?(Item)
|
||||
item = arg
|
||||
else
|
||||
raise 'Invalid arguments'
|
||||
end
|
||||
|
||||
self << item
|
||||
index += 1
|
||||
end
|
||||
end
|
||||
|
||||
# @param [ String ] name
|
||||
# @param [ Hash ] attrs
|
||||
#
|
||||
# @return [ WpItem ]
|
||||
def create_item(name, attrs = {})
|
||||
raise 'wp_target must be set' unless wp_target
|
||||
|
||||
item_class.new(
|
||||
wp_target.uri,
|
||||
attrs.merge(
|
||||
name: name,
|
||||
wp_content_dir: wp_target.wp_content_dir,
|
||||
wp_plugins_dir: wp_target.wp_plugins_dir
|
||||
) { |key, oldval, newval| oldval }
|
||||
)
|
||||
end
|
||||
|
||||
# @param [ WpItems ] other
|
||||
#
|
||||
# @return [ self ]
|
||||
def +(other)
|
||||
other.each { |item| self << item }
|
||||
self
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
# @return [ Class ]
|
||||
def item_class
|
||||
Object.const_get(self.class.to_s.gsub(/.$/, ''))
|
||||
end
|
||||
end
|
||||
|
||||
@@ -1,238 +1,236 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpItems < Array
|
||||
module Detectable
|
||||
|
||||
attr_reader :vulns_file, :item_xpath
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Hash ] options
|
||||
# @option options [ Boolean ] :show_progression Whether or not output the progress bar
|
||||
# @option options [ Boolean ] :only_vulnerable Only check for vulnerable items
|
||||
# @option options [ String ] :exclude_content
|
||||
#
|
||||
# @return [ WpItems ]
|
||||
def aggressive_detection(wp_target, options = {})
|
||||
browser = Browser.instance
|
||||
hydra = browser.hydra
|
||||
targets = targets_items(wp_target, options)
|
||||
progress_bar = progress_bar(targets.size, options)
|
||||
queue_count = 0
|
||||
exist_options = {
|
||||
error_404_hash: wp_target.error_404_hash,
|
||||
homepage_hash: wp_target.homepage_hash,
|
||||
exclude_content: options[:exclude_content] ? %r{#{options[:exclude_content]}} : nil
|
||||
}
|
||||
|
||||
# If we only want the vulnerable ones, the passive detection is ignored
|
||||
# Otherwise, a passive detection is performed, and results will be merged
|
||||
results = options[:only_vulnerable] ? new : passive_detection(wp_target, options)
|
||||
|
||||
targets.each do |target_item|
|
||||
request = browser.forge_request(target_item.url, request_params)
|
||||
|
||||
request.on_complete do |response|
|
||||
progress_bar.progress += 1 if options[:show_progression]
|
||||
|
||||
if target_item.exists?(exist_options, response)
|
||||
if !results.include?(target_item)
|
||||
if !options[:only_vulnerable] || options[:only_vulnerable] && target_item.vulnerable?
|
||||
results << target_item
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
hydra.queue(request)
|
||||
queue_count += 1
|
||||
|
||||
if queue_count >= browser.max_threads
|
||||
hydra.run
|
||||
queue_count = 0
|
||||
puts "Sent #{browser.max_threads} requests ..." if options[:verbose]
|
||||
end
|
||||
end
|
||||
|
||||
# run the remaining requests
|
||||
hydra.run
|
||||
results.sort!
|
||||
results # can't just return results.sort because the #sort returns an array, and we want a WpItems
|
||||
end
|
||||
|
||||
# @param [ Integer ] targets_size
|
||||
# @param [ Hash ] options
|
||||
#
|
||||
# @return [ ProgressBar ]
|
||||
# :nocov:
|
||||
def progress_bar(targets_size, options)
|
||||
if options[:show_progression]
|
||||
ProgressBar.create(
|
||||
format: '%t %a <%B> (%c / %C) %P%% %e',
|
||||
title: ' ', # Used to craete a left margin
|
||||
total: targets_size
|
||||
)
|
||||
end
|
||||
end
|
||||
# :nocov:
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Hash ] options
|
||||
#
|
||||
# @return [ WpItems ]
|
||||
def passive_detection(wp_target, options = {})
|
||||
results = new(wp_target)
|
||||
# improves speed
|
||||
body = remove_base64_images_from_html(Browser.get(wp_target.url).body)
|
||||
page = Nokogiri::HTML(body)
|
||||
names = []
|
||||
|
||||
page.css('link,script,style').each do |tag|
|
||||
%w(href src).each do |attribute|
|
||||
attr_value = tag.attribute(attribute).to_s
|
||||
next unless attr_value
|
||||
|
||||
names << Regexp.last_match[1] if attr_value.match(attribute_pattern(wp_target))
|
||||
end
|
||||
|
||||
next unless tag.name == 'script' || tag.name == 'style'
|
||||
|
||||
code = tag.text.to_s
|
||||
next if code.empty?
|
||||
|
||||
code.scan(code_pattern(wp_target)).flatten.uniq.each do |item_name|
|
||||
names << item_name
|
||||
end
|
||||
end
|
||||
|
||||
names.uniq.each { |name| results.add(name) }
|
||||
|
||||
results.sort!
|
||||
results
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
#
|
||||
# @return [ Regex ]
|
||||
def item_pattern(wp_target)
|
||||
type = to_s.gsub(/Wp/, '').downcase
|
||||
wp_content_dir = wp_target.wp_content_dir
|
||||
wp_content_url = wp_target.uri.merge(wp_content_dir).to_s
|
||||
|
||||
url = /#{wp_content_url.gsub(%r{\A(?:http|https)}, 'https?').gsub('/', '\\\\\?\/')}/i
|
||||
content_dir = %r{(?:#{url}|\\?\/\\?\/?#{wp_content_dir})}i
|
||||
|
||||
%r{#{content_dir}\\?/#{type}\\?/}
|
||||
end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
#
|
||||
# @return [ Regex ]
|
||||
def attribute_pattern(wp_target)
|
||||
/\A#{item_pattern(wp_target)}([^\/]+)/i
|
||||
end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
#
|
||||
# @return [ Regex ]
|
||||
def code_pattern(wp_target)
|
||||
/["'\(]#{item_pattern(wp_target)}([^\\\/\)"']+)/i
|
||||
end
|
||||
|
||||
# The default request parameters
|
||||
#
|
||||
# @return [ Hash ]
|
||||
def request_params; { cache_ttl: 0, followlocation: true } end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ options ] options
|
||||
# @option options [ Boolean ] :only_vulnerable
|
||||
# @option options [ String ] :file The path to the file containing the targets
|
||||
#
|
||||
# @return [ Array<WpItem> ]
|
||||
def targets_items(wp_target, options = {})
|
||||
item_class = self.item_class
|
||||
vulns_file = self.vulns_file
|
||||
|
||||
targets = vulnerable_targets_items(wp_target, item_class, vulns_file)
|
||||
|
||||
unless options[:only_vulnerable]
|
||||
unless options[:file]
|
||||
raise 'A file must be supplied'
|
||||
end
|
||||
|
||||
targets += targets_items_from_file(options[:file], wp_target, item_class, vulns_file)
|
||||
end
|
||||
|
||||
targets.uniq! { |t| t.name }
|
||||
targets.sort_by { rand }
|
||||
end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Class ] item_class
|
||||
# @param [ String ] vulns_file
|
||||
#
|
||||
# @return [ Array<WpItem> ]
|
||||
def vulnerable_targets_items(wp_target, item_class, vulns_file)
|
||||
targets = []
|
||||
json = json(vulns_file)
|
||||
|
||||
[*json].each do |item|
|
||||
targets << create_item(
|
||||
item_class,
|
||||
item.keys.inject,
|
||||
wp_target,
|
||||
vulns_file
|
||||
)
|
||||
end
|
||||
|
||||
targets
|
||||
end
|
||||
|
||||
# @param [ Class ] klass
|
||||
# @param [ String ] name
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @option [ String ] vulns_file
|
||||
#
|
||||
# @return [ WpItem ]
|
||||
def create_item(klass, name, wp_target, vulns_file = nil)
|
||||
klass.new(
|
||||
wp_target.uri,
|
||||
name: name,
|
||||
vulns_file: vulns_file,
|
||||
wp_content_dir: wp_target.wp_content_dir,
|
||||
wp_plugins_dir: wp_target.wp_plugins_dir
|
||||
)
|
||||
end
|
||||
|
||||
# @param [ String ] file
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Class ] item_class
|
||||
# @param [ String ] vulns_file
|
||||
#
|
||||
# @return [ Array<WpItem> ]
|
||||
def targets_items_from_file(file, wp_target, item_class, vulns_file)
|
||||
targets = []
|
||||
|
||||
File.open(file, 'r') do |f|
|
||||
f.readlines.collect do |item_name|
|
||||
targets << create_item(
|
||||
item_class,
|
||||
item_name.strip,
|
||||
wp_target,
|
||||
vulns_file
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
targets
|
||||
end
|
||||
|
||||
# @return [ Class ]
|
||||
def item_class
|
||||
Object.const_get(self.to_s.gsub(/.$/, ''))
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpItems < Array
|
||||
module Detectable
|
||||
|
||||
attr_reader :vulns_file, :item_xpath
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Hash ] options
|
||||
# @option options [ Boolean ] :show_progression Whether or not output the progress bar
|
||||
# @option options [ Boolean ] :only_vulnerable Only check for vulnerable items
|
||||
# @option options [ String ] :exclude_content
|
||||
#
|
||||
# @return [ WpItems ]
|
||||
def aggressive_detection(wp_target, options = {})
|
||||
browser = Browser.instance
|
||||
hydra = browser.hydra
|
||||
targets = targets_items(wp_target, options)
|
||||
progress_bar = progress_bar(targets.size, options)
|
||||
queue_count = 0
|
||||
exist_options = {
|
||||
error_404_hash: wp_target.error_404_hash,
|
||||
homepage_hash: wp_target.homepage_hash,
|
||||
exclude_content: options[:exclude_content] ? %r{#{options[:exclude_content]}} : nil
|
||||
}
|
||||
results = passive_detection(wp_target, options)
|
||||
|
||||
targets.each do |target_item|
|
||||
request = browser.forge_request(target_item.url, request_params)
|
||||
|
||||
request.on_complete do |response|
|
||||
progress_bar.progress += 1 if options[:show_progression]
|
||||
|
||||
if target_item.exists?(exist_options, response)
|
||||
results << target_item unless results.include?(target_item)
|
||||
end
|
||||
end
|
||||
|
||||
hydra.queue(request)
|
||||
queue_count += 1
|
||||
|
||||
if queue_count >= browser.max_threads
|
||||
hydra.run
|
||||
queue_count = 0
|
||||
puts "Sent #{browser.max_threads} requests ..." if options[:verbose]
|
||||
end
|
||||
end
|
||||
|
||||
# run the remaining requests
|
||||
hydra.run
|
||||
|
||||
results.select!(&:vulnerable?) if options[:type] == :vulnerable
|
||||
results.sort!
|
||||
|
||||
results # can't just return results.sort as it would return an array, and we want a WpItems
|
||||
end
|
||||
|
||||
# @param [ Integer ] targets_size
|
||||
# @param [ Hash ] options
|
||||
#
|
||||
# @return [ ProgressBar ]
|
||||
# :nocov:
|
||||
def progress_bar(targets_size, options)
|
||||
if options[:show_progression]
|
||||
ProgressBar.create(
|
||||
format: '%t %a <%B> (%c / %C) %P%% %e',
|
||||
title: ' ', # Used to craete a left margin
|
||||
total: targets_size
|
||||
)
|
||||
end
|
||||
end
|
||||
# :nocov:
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Hash ] options
|
||||
#
|
||||
# @return [ WpItems ]
|
||||
def passive_detection(wp_target, options = {})
|
||||
results = new(wp_target)
|
||||
# improves speed
|
||||
body = remove_base64_images_from_html(Browser.get(wp_target.url).body)
|
||||
page = Nokogiri::HTML(body)
|
||||
names = []
|
||||
|
||||
page.css('link,script,style').each do |tag|
|
||||
%w(href src).each do |attribute|
|
||||
attr_value = tag.attribute(attribute).to_s
|
||||
next unless attr_value
|
||||
|
||||
names << Regexp.last_match[1] if attr_value.match(attribute_pattern(wp_target))
|
||||
end
|
||||
|
||||
next unless tag.name == 'script' || tag.name == 'style'
|
||||
|
||||
code = tag.text.to_s
|
||||
next if code.empty?
|
||||
|
||||
code.scan(code_pattern(wp_target)).flatten.uniq.each do |item_name|
|
||||
names << item_name
|
||||
end
|
||||
end
|
||||
|
||||
names.uniq.each { |name| results.add(name) }
|
||||
|
||||
results.sort!
|
||||
results
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
#
|
||||
# @return [ Regex ]
|
||||
def item_pattern(wp_target)
|
||||
type = to_s.gsub(/Wp/, '').downcase
|
||||
wp_content_dir = wp_target.wp_content_dir
|
||||
wp_content_url = wp_target.uri.merge(wp_content_dir).to_s
|
||||
|
||||
url = /#{wp_content_url.gsub(%r{\A(?:http|https)}, 'https?').gsub('/', '\\\\\?\/')}/i
|
||||
content_dir = %r{(?:#{url}|\\?\/\\?\/?#{wp_content_dir})}i
|
||||
|
||||
%r{#{content_dir}\\?/#{type}\\?/}
|
||||
end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
#
|
||||
# @return [ Regex ]
|
||||
def attribute_pattern(wp_target)
|
||||
/\A#{item_pattern(wp_target)}([^\/]+)/i
|
||||
end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
#
|
||||
# @return [ Regex ]
|
||||
def code_pattern(wp_target)
|
||||
/["'\(]#{item_pattern(wp_target)}([^\\\/\)"']+)/i
|
||||
end
|
||||
|
||||
# The default request parameters
|
||||
#
|
||||
# @return [ Hash ]
|
||||
def request_params; { cache_ttl: 0, followlocation: true } end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ options ] options
|
||||
# @option options [ Boolean ] :only_vulnerable
|
||||
# @option options [ String ] :file The path to the file containing the targets
|
||||
#
|
||||
# @return [ Array<WpItem> ]
|
||||
def targets_items(wp_target, options = {})
|
||||
item_class = self.item_class
|
||||
vulns_file = self.vulns_file
|
||||
|
||||
targets = target_items_from_type(wp_target, item_class, vulns_file, options[:type])
|
||||
|
||||
targets.uniq! { |t| t.name }
|
||||
targets.sort_by { rand }
|
||||
end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Class ] item_class
|
||||
# @param [ String ] vulns_file
|
||||
#
|
||||
# @return [ Array<WpItem> ]
|
||||
def target_items_from_type(wp_target, item_class, vulns_file, type)
|
||||
targets = []
|
||||
json = json(vulns_file)
|
||||
|
||||
case type
|
||||
when :vulnerable
|
||||
items = json.select { |item| !json[item]['vulnerabilities'].empty? }.keys
|
||||
when :popular
|
||||
items = json.select { |item| json[item]['popular'] == true }.keys
|
||||
when :all
|
||||
items = json.keys
|
||||
else
|
||||
raise "Unknown type #{type}"
|
||||
end
|
||||
|
||||
items.each do |item|
|
||||
targets << create_item(
|
||||
item_class,
|
||||
item,
|
||||
wp_target,
|
||||
vulns_file
|
||||
)
|
||||
end
|
||||
|
||||
targets
|
||||
end
|
||||
|
||||
# @param [ Class ] klass
|
||||
# @param [ String ] name
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @option [ String ] vulns_file
|
||||
#
|
||||
# @return [ WpItem ]
|
||||
def create_item(klass, name, wp_target, vulns_file = nil)
|
||||
klass.new(
|
||||
wp_target.uri,
|
||||
name: name,
|
||||
vulns_file: vulns_file,
|
||||
wp_content_dir: wp_target.wp_content_dir,
|
||||
wp_plugins_dir: wp_target.wp_plugins_dir
|
||||
)
|
||||
end
|
||||
|
||||
# @param [ String ] file
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Class ] item_class
|
||||
# @param [ String ] vulns_file
|
||||
#
|
||||
# @return [ Array<WpItem> ]
|
||||
def targets_items_from_file(file, wp_target, item_class, vulns_file)
|
||||
targets = []
|
||||
|
||||
File.open(file, 'r') do |f|
|
||||
f.readlines.collect do |item_name|
|
||||
targets << create_item(
|
||||
item_class,
|
||||
item_name.strip,
|
||||
wp_target,
|
||||
vulns_file
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
targets
|
||||
end
|
||||
|
||||
# @return [ Class ]
|
||||
def item_class
|
||||
Object.const_get(self.to_s.gsub(/.$/, ''))
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -2,17 +2,11 @@
|
||||
|
||||
class WpPlugins < WpItems
|
||||
module Detectable
|
||||
|
||||
# @return [ String ]
|
||||
def vulns_file
|
||||
PLUGINS_VULNS_FILE
|
||||
PLUGINS_FILE
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
# def item_xpath
|
||||
# '//plugin'
|
||||
# end
|
||||
|
||||
# @param [ WpTarget ] wp_target
|
||||
# @param [ Hash ] options
|
||||
#
|
||||
|
||||
@@ -5,13 +5,7 @@ class WpThemes < WpItems
|
||||
|
||||
# @return [ String ]
|
||||
def vulns_file
|
||||
THEMES_VULNS_FILE
|
||||
THEMES_FILE
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
# def item_xpath
|
||||
# '//theme'
|
||||
# end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
@@ -38,6 +38,7 @@ class WpUsers < WpItems
|
||||
junk = get_equal_string_end(display_names)
|
||||
unless junk.nil? or junk.empty?
|
||||
self.each do |u|
|
||||
u.display_name ||= ''
|
||||
u.display_name = u.display_name.sub(/#{Regexp.escape(junk)}$/, '')
|
||||
end
|
||||
end
|
||||
|
||||
@@ -6,7 +6,6 @@ DATA_DIR = File.join(ROOT_DIR, 'data')
|
||||
CONF_DIR = File.join(ROOT_DIR, 'conf')
|
||||
CACHE_DIR = File.join(ROOT_DIR, 'cache')
|
||||
WPSCAN_LIB_DIR = File.join(LIB_DIR, 'wpscan')
|
||||
WPSTOOLS_LIB_DIR = File.join(LIB_DIR, 'wpstools')
|
||||
UPDATER_LIB_DIR = File.join(LIB_DIR, 'updater')
|
||||
COMMON_LIB_DIR = File.join(LIB_DIR, 'common')
|
||||
MODELS_LIB_DIR = File.join(COMMON_LIB_DIR, 'models')
|
||||
@@ -17,24 +16,19 @@ LOG_FILE = File.join(ROOT_DIR, 'log.txt')
|
||||
# Plugins directories
|
||||
COMMON_PLUGINS_DIR = File.join(COMMON_LIB_DIR, 'plugins')
|
||||
WPSCAN_PLUGINS_DIR = File.join(WPSCAN_LIB_DIR, 'plugins') # Not used ATM
|
||||
WPSTOOLS_PLUGINS_DIR = File.join(WPSTOOLS_LIB_DIR, 'plugins')
|
||||
|
||||
# Data files
|
||||
PLUGINS_FILE = File.join(DATA_DIR, 'plugins.txt')
|
||||
PLUGINS_FULL_FILE = File.join(DATA_DIR, 'plugins_full.txt')
|
||||
PLUGINS_VULNS_FILE = File.join(DATA_DIR, 'plugin_vulns.json')
|
||||
THEMES_FILE = File.join(DATA_DIR, 'themes.txt')
|
||||
THEMES_FULL_FILE = File.join(DATA_DIR, 'themes_full.txt')
|
||||
THEMES_VULNS_FILE = File.join(DATA_DIR, 'theme_vulns.json')
|
||||
WP_VULNS_FILE = File.join(DATA_DIR, 'wp_vulns.json')
|
||||
WP_VERSIONS_FILE = File.join(DATA_DIR, 'wp_versions.xml')
|
||||
LOCAL_FILES_FILE = File.join(DATA_DIR, 'local_vulnerable_files.xml')
|
||||
# VULNS_XSD = File.join(DATA_DIR, 'vuln.xsd')
|
||||
WP_VERSIONS_XSD = File.join(DATA_DIR, 'wp_versions.xsd')
|
||||
LOCAL_FILES_XSD = File.join(DATA_DIR, 'local_vulnerable_files.xsd')
|
||||
USER_AGENTS_FILE = File.join(DATA_DIR, 'user-agents.txt')
|
||||
WORDPRESSES_FILE = File.join(DATA_DIR, 'wordpresses.json')
|
||||
PLUGINS_FILE = File.join(DATA_DIR, 'plugins.json')
|
||||
THEMES_FILE = File.join(DATA_DIR, 'themes.json')
|
||||
WP_VERSIONS_FILE = File.join(DATA_DIR, 'wp_versions.xml')
|
||||
LOCAL_FILES_FILE = File.join(DATA_DIR, 'local_vulnerable_files.xml')
|
||||
WP_VERSIONS_XSD = File.join(DATA_DIR, 'wp_versions.xsd')
|
||||
LOCAL_FILES_XSD = File.join(DATA_DIR, 'local_vulnerable_files.xsd')
|
||||
USER_AGENTS_FILE = File.join(DATA_DIR, 'user-agents.txt')
|
||||
LAST_UPDATE_FILE = File.join(DATA_DIR, '.last_update')
|
||||
|
||||
WPSCAN_VERSION = '2.5.1'
|
||||
WPSCAN_VERSION = '2.9'
|
||||
|
||||
$LOAD_PATH.unshift(LIB_DIR)
|
||||
$LOAD_PATH.unshift(WPSCAN_LIB_DIR)
|
||||
@@ -42,7 +36,7 @@ $LOAD_PATH.unshift(MODELS_LIB_DIR)
|
||||
|
||||
def kali_linux?
|
||||
begin
|
||||
File.readlines("/etc/debian_version").grep(/^kali/i).any?
|
||||
File.readlines('/etc/debian_version').grep(/^kali/i).any?
|
||||
rescue
|
||||
false
|
||||
end
|
||||
@@ -50,14 +44,18 @@ end
|
||||
|
||||
require 'environment'
|
||||
|
||||
def escape_glob(s)
|
||||
s.gsub(/[\\\{\}\[\]\*\?]/) { |x| '\\' + x }
|
||||
end
|
||||
|
||||
# TODO : add an exclude pattern ?
|
||||
def require_files_from_directory(absolute_dir_path, files_pattern = '*.rb')
|
||||
files = Dir[File.join(absolute_dir_path, files_pattern)]
|
||||
files = Dir[File.join(escape_glob(absolute_dir_path), files_pattern)]
|
||||
|
||||
# Files in the root dir are loaded first, then those in the subdirectories
|
||||
files.sort_by { |file| [file.count("/"), file] }.each do |f|
|
||||
files.sort_by { |file| [file.count('/'), file] }.each do |f|
|
||||
f = File.expand_path(f)
|
||||
#puts "require #{f}" # Used for debug
|
||||
# puts "require #{f}" # Used for debug
|
||||
require f
|
||||
end
|
||||
end
|
||||
@@ -80,6 +78,20 @@ def missing_db_file?
|
||||
false
|
||||
end
|
||||
|
||||
def last_update
|
||||
date = nil
|
||||
if File.exists?(LAST_UPDATE_FILE)
|
||||
content = File.read(LAST_UPDATE_FILE)
|
||||
date = Time.parse(content) rescue nil
|
||||
end
|
||||
date
|
||||
end
|
||||
|
||||
def update_required?
|
||||
date = last_update
|
||||
(true if date.nil?) or (date < 5.days.ago)
|
||||
end
|
||||
|
||||
# Define colors
|
||||
def colorize(text, color_code)
|
||||
if $COLORSWITCH
|
||||
@@ -110,19 +122,21 @@ def blue(text)
|
||||
end
|
||||
|
||||
def critical(text)
|
||||
red(text)
|
||||
$exit_code += 1 if defined?($exit_code) # hack for undefined var via rspec
|
||||
"#{red('[!]')} #{text}"
|
||||
end
|
||||
|
||||
def warning(text)
|
||||
amber(text)
|
||||
$exit_code += 1 if defined?($exit_code) # hack for undefined var via rspec
|
||||
"#{amber('[!]')} #{text}"
|
||||
end
|
||||
|
||||
def info(text)
|
||||
green(text)
|
||||
"#{green('[+]')} #{text}"
|
||||
end
|
||||
|
||||
def notice(text)
|
||||
blue(text)
|
||||
"#{blue('[i]')} #{text}"
|
||||
end
|
||||
|
||||
# our 1337 banner
|
||||
@@ -137,7 +151,7 @@ def banner
|
||||
puts
|
||||
puts ' WordPress Security Scanner by the WPScan Team '
|
||||
puts " Version #{WPSCAN_VERSION}"
|
||||
puts ' Sponsored by the RandomStorm Open Source Initiative'
|
||||
puts ' Sponsored by Sucuri - https://sucuri.net'
|
||||
puts ' @_WPScan_, @ethicalhack3r, @erwan_lr, pvdl, @_FireFart_'
|
||||
puts '_______________________________________________________________'
|
||||
puts
|
||||
|
||||
@@ -3,10 +3,9 @@
|
||||
# DB Updater
|
||||
class DbUpdater
|
||||
FILES = %w(
|
||||
local_vulnerable_files.xml local_vulnerable_files.xsd malwares.txt
|
||||
plugins_full.txt plugins.txt themes_full.txt themes.txt
|
||||
local_vulnerable_files.xml local_vulnerable_files.xsd
|
||||
timthumbs.txt user-agents.txt wp_versions.xml wp_versions.xsd
|
||||
plugin_vulns.json theme_vulns.json wp_vulns.json
|
||||
wordpresses.json plugins.json themes.json LICENSE
|
||||
)
|
||||
|
||||
attr_reader :repo_directory
|
||||
@@ -22,13 +21,14 @@ class DbUpdater
|
||||
def request_params
|
||||
{
|
||||
ssl_verifyhost: 2,
|
||||
ssl_verifypeer: true
|
||||
ssl_verifypeer: true,
|
||||
accept_encoding: 'gzip, deflate'
|
||||
}
|
||||
end
|
||||
|
||||
# @return [ String ] The raw file URL associated with the given filename
|
||||
def remote_file_url(filename)
|
||||
"https://raw.githubusercontent.com/wpscanteam/vulndb/master/#{filename}"
|
||||
"https://wpvulndb.com/data/#{filename}"
|
||||
end
|
||||
|
||||
# @return [ String ] The checksum of the associated remote filename
|
||||
@@ -36,8 +36,8 @@ class DbUpdater
|
||||
url = "#{remote_file_url(filename)}.sha512"
|
||||
|
||||
res = Browser.get(url, request_params)
|
||||
fail "Unable to get #{url}" unless res.code == 200
|
||||
res.body
|
||||
fail DownloadError, res if res.timed_out? || res.code != 200
|
||||
res.body.chomp
|
||||
end
|
||||
|
||||
def local_file_path(filename)
|
||||
@@ -72,8 +72,8 @@ class DbUpdater
|
||||
file_url = remote_file_url(filename)
|
||||
|
||||
res = Browser.get(file_url, request_params)
|
||||
fail "Error while downloading #{file_url}" unless res.code == 200
|
||||
File.write(file_path, res.body)
|
||||
fail DownloadError, res if res.timed_out? || res.code != 200
|
||||
File.open(file_path, 'wb') { |f| f.write(res.body) }
|
||||
|
||||
local_file_checksum(filename)
|
||||
end
|
||||
@@ -96,6 +96,7 @@ class DbUpdater
|
||||
puts ' [i] Downloading new file' if verbose
|
||||
dl_checksum = download(filename)
|
||||
puts " [i] Downloaded File Checksum: #{dl_checksum}" if verbose
|
||||
puts " [i] Database File Checksum : #{db_checksum}" if verbose
|
||||
|
||||
unless dl_checksum == db_checksum
|
||||
fail "#{filename}: checksums do not match"
|
||||
@@ -111,5 +112,8 @@ class DbUpdater
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
# write last_update date to file
|
||||
File.write(LAST_UPDATE_FILE, Time.now)
|
||||
end
|
||||
end
|
||||
|
||||
33
lib/common/errors.rb
Normal file
33
lib/common/errors.rb
Normal file
@@ -0,0 +1,33 @@
|
||||
|
||||
# HTTP Error
|
||||
class HttpError < StandardError
|
||||
attr_reader :response
|
||||
|
||||
# @param [ Typhoeus::Response ] response
|
||||
def initialize(response)
|
||||
@response = response
|
||||
end
|
||||
|
||||
def failure_details
|
||||
msg = response.effective_url
|
||||
|
||||
if response.code == 0 || response.timed_out?
|
||||
msg += " (#{response.return_message})"
|
||||
else
|
||||
msg += " (status: #{response.code})"
|
||||
end
|
||||
|
||||
msg
|
||||
end
|
||||
|
||||
def message
|
||||
"HTTP Error: #{failure_details}"
|
||||
end
|
||||
end
|
||||
|
||||
# Used in the Updater
|
||||
class DownloadError < HttpError
|
||||
def message
|
||||
"Unable to get #{failure_details}"
|
||||
end
|
||||
end
|
||||
@@ -49,11 +49,11 @@ end
|
||||
|
||||
# Override for puts to enable logging
|
||||
def puts(o = '')
|
||||
# remove color for logging
|
||||
if o.respond_to?(:gsub)
|
||||
temp = o.gsub(/\e\[\d+m/, '')
|
||||
if $log && o.respond_to?(:gsub)
|
||||
temp = o.gsub(/\e\[\d+m/, '') # remove color for logging
|
||||
File.open(LOG_FILE, 'a+') { |f| f.puts(temp) }
|
||||
end
|
||||
|
||||
super(o)
|
||||
end
|
||||
|
||||
@@ -78,7 +78,7 @@ module Terminal
|
||||
|
||||
class Style
|
||||
@@defaults = {
|
||||
:border_x => "-", :border_y => "|", :border_i => "+",
|
||||
:border_x => '-', :border_y => '|', :border_i => '+',
|
||||
:padding_left => 1, :padding_right => 1,
|
||||
:margin_left => '',
|
||||
:width => nil, :alignment => nil
|
||||
@@ -102,7 +102,20 @@ class Numeric
|
||||
def bytes_to_human
|
||||
units = %w{B KB MB GB TB}
|
||||
e = (Math.log(self)/Math.log(1024)).floor
|
||||
s = "%.3f" % (to_f / 1024**e)
|
||||
s = '%.3f' % (to_f / 1024**e)
|
||||
s.sub(/\.?0*$/, ' ' + units[e])
|
||||
end
|
||||
end
|
||||
|
||||
# time calculations
|
||||
class Fixnum
|
||||
SECONDS_IN_DAY = 24 * 60 * 60
|
||||
|
||||
def days
|
||||
self * SECONDS_IN_DAY
|
||||
end
|
||||
|
||||
def ago
|
||||
Time.now - self
|
||||
end
|
||||
end
|
||||
|
||||
@@ -42,11 +42,12 @@ class Vulnerability
|
||||
# @return [ Vulnerability ]
|
||||
def self.load_from_json_item(json_item)
|
||||
references = {}
|
||||
references['id'] = [json_item['id']]
|
||||
|
||||
%w(id url cve secunia osvdb metasploit exploitdb).each do |key|
|
||||
if json_item[key]
|
||||
json_item[key] = [json_item[key]] if json_item[key].class != Array
|
||||
references[key] = json_item[key]
|
||||
%w(url cve secunia osvdb metasploit exploitdb).each do |key|
|
||||
if json_item['references'][key]
|
||||
json_item['references'][key] = [json_item['references'][key]] if json_item['references'][key].class != Array
|
||||
references[key] = json_item['references'][key]
|
||||
end
|
||||
end
|
||||
|
||||
@@ -54,7 +55,7 @@ class Vulnerability
|
||||
json_item['title'],
|
||||
json_item['type'],
|
||||
references,
|
||||
json_item['fixed_in'],
|
||||
json_item['fixed_in']
|
||||
)
|
||||
end
|
||||
|
||||
|
||||
@@ -2,21 +2,22 @@
|
||||
|
||||
class Vulnerability
|
||||
module Output
|
||||
|
||||
# output the vulnerability
|
||||
def output(verbose = false)
|
||||
puts
|
||||
puts "#{critical('[!]')} Title: #{title}"
|
||||
puts critical("Title: #{title}")
|
||||
|
||||
references.each do |key, urls|
|
||||
methodname = "url_#{key}"
|
||||
|
||||
urls.each do |u|
|
||||
next unless respond_to?(methodname)
|
||||
url = send(methodname, u)
|
||||
puts " Reference: #{url}" if url
|
||||
end
|
||||
end
|
||||
if !fixed_in.nil?
|
||||
puts "#{notice('[i]')} Fixed in: #{fixed_in}"
|
||||
end
|
||||
|
||||
puts notice("Fixed in: #{fixed_in}") if fixed_in
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -6,31 +6,39 @@ class Vulnerability
|
||||
def url_metasploit(module_path)
|
||||
# remove leading slash
|
||||
module_path = module_path.sub(/^\//, '')
|
||||
"http://www.rapid7.com/db/modules/#{module_path}"
|
||||
"https://www.rapid7.com/db/modules/#{module_path}"
|
||||
end
|
||||
|
||||
def url_url(url)
|
||||
url
|
||||
end
|
||||
|
||||
def url_cve(cve)
|
||||
"http://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-#{cve}"
|
||||
def url_cve(id)
|
||||
"https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-#{id}"
|
||||
end
|
||||
|
||||
def url_osvdb(id)
|
||||
"http://osvdb.org/#{id}"
|
||||
"http://osvdb.org/show/osvdb/#{id}"
|
||||
end
|
||||
|
||||
def url_secunia(id)
|
||||
"https://secunia.com/advisories/#{id}"
|
||||
"https://secunia.com/advisories/#{id}/"
|
||||
end
|
||||
|
||||
def url_exploitdb(id)
|
||||
"http://www.exploit-db.com/exploits/#{id}/"
|
||||
"https://www.exploit-db.com/exploits/#{id}/"
|
||||
end
|
||||
|
||||
def url_id(id)
|
||||
"https://wpvulndb.com/vulnerabilities/#{id}"
|
||||
end
|
||||
|
||||
def url_packetstorm(id)
|
||||
"http://packetstormsecurity.com/files/#{id}/"
|
||||
end
|
||||
|
||||
def url_securityfocus(id)
|
||||
"http://www.securityfocus.com/bid/#{id}/"
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -22,7 +22,7 @@ class WpItem
|
||||
# @return [ Array ]
|
||||
# Make it private ?
|
||||
def allowed_options
|
||||
[:name, :wp_content_dir, :wp_plugins_dir, :path, :version, :vulns_file]
|
||||
[:name, :wp_content_dir, :wp_plugins_dir, :path, :version, :db_file]
|
||||
end
|
||||
|
||||
# @param [ URI ] target_base_uri
|
||||
@@ -30,7 +30,6 @@ class WpItem
|
||||
#
|
||||
# @return [ WpItem ]
|
||||
def initialize(target_base_uri, options = {})
|
||||
|
||||
options[:wp_content_dir] ||= 'wp-content'
|
||||
options[:wp_plugins_dir] ||= options[:wp_content_dir] + '/plugins'
|
||||
|
||||
@@ -38,6 +37,27 @@ class WpItem
|
||||
forge_uri(target_base_uri)
|
||||
end
|
||||
|
||||
def identifier
|
||||
@identifier ||= name
|
||||
end
|
||||
|
||||
# @return [ Hash ]
|
||||
def db_data
|
||||
@db_data ||= json(db_file)[identifier] || {}
|
||||
end
|
||||
|
||||
def latest_version
|
||||
db_data['latest_version']
|
||||
end
|
||||
|
||||
def last_updated
|
||||
db_data['last_ipdated']
|
||||
end
|
||||
|
||||
def popular?
|
||||
db_data['popular']
|
||||
end
|
||||
|
||||
# @param [ Hash ] options
|
||||
#
|
||||
# @return [ void ]
|
||||
|
||||
@@ -12,7 +12,9 @@ class WpItem
|
||||
|
||||
# @return [ String,nil ] The url to the readme file, nil if not found
|
||||
def readme_url
|
||||
%w{readme.txt README.txt}.each do |readme|
|
||||
# See https://github.com/wpscanteam/wpscan/pull/737#issuecomment-66375445
|
||||
# for any question about the order
|
||||
%w{readme.txt README.txt Readme.txt ReadMe.txt README.TXT readme.TXT}.each do |readme|
|
||||
url = @uri.merge(readme).to_s
|
||||
return url if url_is_200?(url)
|
||||
end
|
||||
|
||||
@@ -5,20 +5,25 @@ class WpItem
|
||||
|
||||
# @return [ Void ]
|
||||
def output(verbose = false)
|
||||
outdated = VersionCompare.lesser?(version, latest_version) if latest_version
|
||||
|
||||
puts
|
||||
puts "#{info('[+]')} Name: #{self}" #this will also output the version number if detected
|
||||
puts info("Name: #{self}") #this will also output the version number if detected
|
||||
puts " | Latest version: #{latest_version} #{'(up to date)' if version}" if latest_version && !outdated
|
||||
puts " | Last updated: #{last_updated}" if last_updated
|
||||
puts " | Location: #{url}"
|
||||
#puts " | WordPress: #{wordpress_url}" if wordpress_org_item?
|
||||
puts " | Readme: #{readme_url}" if has_readme?
|
||||
puts " | Changelog: #{changelog_url}" if has_changelog?
|
||||
puts "#{warning('[!]')} Directory listing is enabled: #{url}" if has_directory_listing?
|
||||
puts "#{warning('[!]')} An error_log file has been found: #{error_log_url}" if has_error_log?
|
||||
puts warning("The version is out of date, the latest version is #{latest_version}") if latest_version && outdated
|
||||
|
||||
puts warning("Directory listing is enabled: #{url}") if has_directory_listing?
|
||||
puts warning("An error_log file has been found: #{error_log_url}") if has_error_log?
|
||||
|
||||
additional_output(verbose) if respond_to?(:additional_output)
|
||||
|
||||
if version.nil? && vulnerabilities.length > 0
|
||||
puts
|
||||
puts "#{warning('[+]')} We could not determine a version so all vulnerabilities are printed out"
|
||||
puts warning('We could not determine a version so all vulnerabilities are printed out')
|
||||
end
|
||||
|
||||
vulnerabilities.output
|
||||
|
||||
@@ -1,29 +1,53 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpItem
|
||||
attr_writer :version
|
||||
|
||||
module Versionable
|
||||
|
||||
# Get the version from the readme.txt
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def version
|
||||
unless @version
|
||||
# This check is needed because readme_url can return nil
|
||||
if has_readme?
|
||||
response = Browser.get(readme_url)
|
||||
@version = response.body[%r{stable tag: #{WpVersion.version_pattern}}i, 1]
|
||||
end
|
||||
end
|
||||
@version
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def to_s
|
||||
item_version = self.version
|
||||
"#@name#{' - v' + item_version.strip if item_version}"
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpItem
|
||||
attr_writer :version
|
||||
|
||||
module Versionable
|
||||
|
||||
# Get the version from the readme.txt
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def version
|
||||
unless @version
|
||||
# This check is needed because readme_url can return nil
|
||||
if has_readme?
|
||||
response = Browser.get(readme_url)
|
||||
@version = extract_version(response.body)
|
||||
end
|
||||
end
|
||||
@version
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def to_s
|
||||
item_version = self.version
|
||||
"#{@name}#{' - v' + item_version.strip if item_version}"
|
||||
end
|
||||
|
||||
# Extracts the version number from a given string/body
|
||||
#
|
||||
# @return [ String ] detected version
|
||||
def extract_version(body)
|
||||
version = body[/\b(?:stable tag|version):\s*(?!trunk)([0-9a-z\.-]+)/i, 1]
|
||||
if version.nil? || version !~ /[0-9]+/
|
||||
extracted_versions = body.scan(/[=]+\s+(?:v(?:ersion)?\s*)?([0-9\.-]+)[ \ta-z0-9\(\)\.-]*[=]+/i)
|
||||
return if extracted_versions.nil? || extracted_versions.length == 0
|
||||
extracted_versions.flatten!
|
||||
# must contain at least one number
|
||||
extracted_versions = extracted_versions.select { |x| x =~ /[0-9]+/ }
|
||||
sorted = extracted_versions.sort { |x,y|
|
||||
begin
|
||||
Gem::Version.new(x) <=> Gem::Version.new(y)
|
||||
rescue
|
||||
0
|
||||
end
|
||||
}
|
||||
return sorted.last
|
||||
else
|
||||
return version
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
@@ -2,28 +2,23 @@
|
||||
|
||||
class WpItem
|
||||
module Vulnerable
|
||||
attr_accessor :vulns_file, :identifier
|
||||
attr_accessor :db_file, :identifier
|
||||
|
||||
# Get the vulnerabilities associated to the WpItem
|
||||
# Filters out already fixed vulnerabilities
|
||||
#
|
||||
# @return [ Vulnerabilities ]
|
||||
def vulnerabilities
|
||||
json = json(vulns_file)
|
||||
vulnerabilities = Vulnerabilities.new
|
||||
return @vulnerabilities if @vulnerabilities
|
||||
|
||||
json.each do |item|
|
||||
asset = item[identifier]
|
||||
@vulnerabilities = Vulnerabilities.new
|
||||
|
||||
if asset
|
||||
asset['vulnerabilities'].each do |vulnerability|
|
||||
vulnerability = Vulnerability.load_from_json_item(vulnerability)
|
||||
vulnerabilities << vulnerability if vulnerable_to?(vulnerability)
|
||||
end
|
||||
end
|
||||
[*db_data['vulnerabilities']].each do |vulnerability|
|
||||
vulnerability = Vulnerability.load_from_json_item(vulnerability)
|
||||
@vulnerabilities << vulnerability if vulnerable_to?(vulnerability)
|
||||
end
|
||||
|
||||
vulnerabilities
|
||||
@vulnerabilities
|
||||
end
|
||||
|
||||
def vulnerable?
|
||||
|
||||
@@ -1,10 +1,6 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
require 'wp_plugin/vulnerable'
|
||||
|
||||
class WpPlugin < WpItem
|
||||
include WpPlugin::Vulnerable
|
||||
|
||||
# Sets the @uri
|
||||
#
|
||||
# @param [ URI ] target_base_uri The URI of the wordpress blog
|
||||
@@ -14,4 +10,7 @@ class WpPlugin < WpItem
|
||||
@uri = target_base_uri.merge(URI.encode(wp_plugins_dir + '/' + name + '/'))
|
||||
end
|
||||
|
||||
def db_file
|
||||
@db_file ||= PLUGINS_FILE
|
||||
end
|
||||
end
|
||||
|
||||
@@ -1,20 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpPlugin < WpItem
|
||||
module Vulnerable
|
||||
|
||||
# @return [ String ] The path to the file containing vulnerabilities
|
||||
def vulns_file
|
||||
unless @vulns_file
|
||||
@vulns_file = PLUGINS_VULNS_FILE
|
||||
end
|
||||
@vulns_file
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def identifier
|
||||
@name
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
@@ -2,7 +2,6 @@
|
||||
|
||||
require 'wp_theme/findable'
|
||||
require 'wp_theme/versionable'
|
||||
require 'wp_theme/vulnerable'
|
||||
require 'wp_theme/info'
|
||||
require 'wp_theme/output'
|
||||
require 'wp_theme/childtheme'
|
||||
@@ -10,7 +9,6 @@ require 'wp_theme/childtheme'
|
||||
class WpTheme < WpItem
|
||||
extend WpTheme::Findable
|
||||
include WpTheme::Versionable
|
||||
include WpTheme::Vulnerable
|
||||
include WpTheme::Info
|
||||
include WpTheme::Output
|
||||
include WpTheme::Childtheme
|
||||
@@ -33,4 +31,7 @@ class WpTheme < WpItem
|
||||
@uri.merge('style.css').to_s
|
||||
end
|
||||
|
||||
def db_file
|
||||
@db_file ||= THEMES_FILE
|
||||
end
|
||||
end
|
||||
|
||||
@@ -3,6 +3,10 @@
|
||||
class WpTheme < WpItem
|
||||
module Childtheme
|
||||
|
||||
def parent_theme_limit
|
||||
3
|
||||
end
|
||||
|
||||
def is_child_theme?
|
||||
return true unless @theme_template.nil?
|
||||
false
|
||||
@@ -10,7 +14,7 @@ class WpTheme < WpItem
|
||||
|
||||
def get_parent_theme_style_url
|
||||
if is_child_theme?
|
||||
return style_url.sub("/#{name}/style.css", "/#@theme_template/style.css")
|
||||
return style_url.sub("/#{name}/style.css", "/#{@theme_template}/style.css")
|
||||
end
|
||||
nil
|
||||
end
|
||||
|
||||
@@ -30,17 +30,14 @@ class WpTheme < WpItem
|
||||
response = Browser.get_and_follow_location(target_uri.to_s)
|
||||
|
||||
# https + domain is optional because of relative links
|
||||
matches = /(?:https?:\/\/[^"']+)?\/([^\/]+)\/themes\/([^"'\/]+)[^"']*\/style.css/i.match(response.body)
|
||||
if matches
|
||||
return new(
|
||||
target_uri,
|
||||
{
|
||||
name: matches[2],
|
||||
referenced_url: matches[0],
|
||||
wp_content_dir: matches[1]
|
||||
}
|
||||
)
|
||||
end
|
||||
return unless response.body =~ %r{(?:https?://[^"']+/)?([^/\s]+)/themes/([^"'/]+)[^"']*/style.css}i
|
||||
|
||||
new(
|
||||
target_uri,
|
||||
name: Regexp.last_match[2],
|
||||
referenced_url: Regexp.last_match[0],
|
||||
wp_content_dir: Regexp.last_match[1]
|
||||
)
|
||||
end
|
||||
|
||||
# @param [ URI ] target_uri
|
||||
@@ -50,7 +47,6 @@ class WpTheme < WpItem
|
||||
body = Browser.get(target_uri.to_s).body
|
||||
regexp = %r{<meta name="generator" content="([^\s"]+)\s?([^"]+)?" />\s+<meta name="generator" content="WooFramework\s?([^"]+)?" />}
|
||||
|
||||
|
||||
if matches = regexp.match(body)
|
||||
woo_theme_name = matches[1]
|
||||
woo_theme_version = matches[2]
|
||||
@@ -58,10 +54,8 @@ class WpTheme < WpItem
|
||||
|
||||
return new(
|
||||
target_uri,
|
||||
{
|
||||
name: woo_theme_name,
|
||||
version: woo_theme_version
|
||||
}
|
||||
name: woo_theme_name,
|
||||
version: woo_theme_version
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
@@ -10,16 +10,16 @@ class WpTheme
|
||||
theme_desc = verbose ? @theme_description : truncate(@theme_description, 100)
|
||||
puts " | Style URL: #{style_url}"
|
||||
puts " | Referenced style.css: #{referenced_url}" if referenced_url && referenced_url != style_url
|
||||
puts " | Theme Name: #@theme_name" if @theme_name
|
||||
puts " | Theme URI: #@theme_uri" if @theme_uri
|
||||
puts " | Theme Name: #{@theme_name}" if @theme_name
|
||||
puts " | Theme URI: #{@theme_uri}" if @theme_uri
|
||||
puts " | Description: #{theme_desc}"
|
||||
puts " | Author: #@theme_author" if @theme_author
|
||||
puts " | Author URI: #@theme_author_uri" if @theme_author_uri
|
||||
puts " | Template: #@theme_template" if @theme_template and verbose
|
||||
puts " | License: #@theme_license" if @theme_license and verbose
|
||||
puts " | License URI: #@theme_license_uri" if @theme_license_uri and verbose
|
||||
puts " | Tags: #@theme_tags" if @theme_tags and verbose
|
||||
puts " | Text Domain: #@theme_text_domain" if @theme_text_domain and verbose
|
||||
puts " | Author: #{@theme_author}" if @theme_author
|
||||
puts " | Author URI: #{@theme_author_uri}" if @theme_author_uri
|
||||
puts " | Template: #{@theme_template}" if @theme_template and verbose
|
||||
puts " | License: #{@theme_license}" if @theme_license and verbose
|
||||
puts " | License URI: #{@theme_license_uri}" if @theme_license_uri and verbose
|
||||
puts " | Tags: #{@theme_tags}" if @theme_tags and verbose
|
||||
puts " | Text Domain: #{@theme_text_domain}" if @theme_text_domain and verbose
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
@@ -2,16 +2,8 @@
|
||||
|
||||
class WpTheme < WpItem
|
||||
module Versionable
|
||||
|
||||
def version
|
||||
unless @version
|
||||
@version = Browser.get(style_url).body[%r{Version:\s*([^\s]+)}i, 1]
|
||||
|
||||
# Get Version from readme.txt
|
||||
@version ||= super
|
||||
end
|
||||
@version
|
||||
@version ||= Browser.get(style_url).body[%r{Version:\s*(?!trunk)([0-9a-z\.-]+)}i, 1]
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
@@ -1,19 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpTheme < WpItem
|
||||
module Vulnerable
|
||||
|
||||
# @return [ String ] The path to the file containing vulnerabilities
|
||||
def vulns_file
|
||||
unless @vulns_file
|
||||
@vulns_file = THEMES_VULNS_FILE
|
||||
end
|
||||
@vulns_file
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def identifier
|
||||
@name
|
||||
end
|
||||
end
|
||||
end
|
||||
@@ -5,7 +5,7 @@ class WpTimthumb < WpItem
|
||||
|
||||
def output(verbose = false)
|
||||
puts
|
||||
puts "#{info('[+]')} #{self}" #this will also output the version number if detected
|
||||
puts info("#{self}") #this will also output the version number if detected
|
||||
|
||||
vulnerabilities.output
|
||||
end
|
||||
|
||||
@@ -15,7 +15,7 @@ class WpTimthumb < WpItem
|
||||
end
|
||||
|
||||
def check_rce_132
|
||||
return rce_132_vuln unless VersionCompare.lesser_or_equal?('1.33', version)
|
||||
rce_132_vuln unless VersionCompare.lesser_or_equal?('1.33', version)
|
||||
end
|
||||
|
||||
# Vulnerable versions : > 1.35 (or >= 2.0) and < 2.8.14
|
||||
@@ -24,7 +24,7 @@ class WpTimthumb < WpItem
|
||||
|
||||
response = Browser.get(uri.merge('?webshot=1&src=http://' + default_allowed_domains.sample))
|
||||
|
||||
return rce_webshot_vuln unless response.body =~ /WEBSHOT_ENABLED == true/
|
||||
rce_webshot_vuln unless response.body =~ /WEBSHOT_ENABLED == true/
|
||||
end
|
||||
|
||||
# @return [ Array<String> ] The default allowed domains (between the 2.0 and 2.8.13)
|
||||
|
||||
@@ -1,81 +1,81 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
require 'wp_user/existable'
|
||||
require 'wp_user/brute_forcable'
|
||||
|
||||
class WpUser < WpItem
|
||||
include WpUser::Existable
|
||||
include WpUser::BruteForcable
|
||||
|
||||
attr_accessor :id, :login, :display_name, :password
|
||||
|
||||
# @return [ Array<Symbol> ]
|
||||
def allowed_options; [:id, :login, :display_name, :password] end
|
||||
|
||||
# @return [ URI ] The uri to the author page
|
||||
def uri
|
||||
if id
|
||||
return @uri.merge("?author=#{id}")
|
||||
else
|
||||
raise 'The id is nil'
|
||||
end
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def login_url
|
||||
unless @login_url
|
||||
@login_url = @uri.merge('wp-login.php').to_s
|
||||
|
||||
# Let's check if the login url is redirected (to https url for example)
|
||||
if redirection = redirection(@login_url)
|
||||
@login_url = redirection
|
||||
end
|
||||
end
|
||||
|
||||
@login_url
|
||||
end
|
||||
|
||||
def redirection(url)
|
||||
redirection = nil
|
||||
response = Browser.get(url)
|
||||
|
||||
if response.code == 301 || response.code == 302
|
||||
redirection = response.headers_hash['location']
|
||||
|
||||
# Let's check if there is a redirection in the redirection
|
||||
if other_redirection = redirection(redirection)
|
||||
redirection = other_redirection
|
||||
end
|
||||
end
|
||||
|
||||
redirection
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def to_s
|
||||
s = "#{id}"
|
||||
s << " | #{login}" if login
|
||||
s << " | #{display_name}" if display_name
|
||||
s
|
||||
end
|
||||
|
||||
# @param [ WpUser ] other
|
||||
def <=>(other)
|
||||
id <=> other.id
|
||||
end
|
||||
|
||||
# @param [ WpUser ] other
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
def ==(other)
|
||||
self === other
|
||||
end
|
||||
|
||||
# @param [ WpUser ] other
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
def ===(other)
|
||||
id === other.id && login === other.login
|
||||
end
|
||||
|
||||
end
|
||||
# encoding: UTF-8
|
||||
|
||||
require 'wp_user/existable'
|
||||
require 'wp_user/brute_forcable'
|
||||
|
||||
class WpUser < WpItem
|
||||
include WpUser::Existable
|
||||
include WpUser::BruteForcable
|
||||
|
||||
attr_accessor :id, :login, :display_name, :password
|
||||
|
||||
# @return [ Array<Symbol> ]
|
||||
def allowed_options; [:id, :login, :display_name, :password] end
|
||||
|
||||
# @return [ URI ] The uri to the author page
|
||||
def uri
|
||||
if id
|
||||
@uri.merge("?author=#{id}")
|
||||
else
|
||||
raise 'The id is nil'
|
||||
end
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def login_url
|
||||
unless @login_url
|
||||
@login_url = @uri.merge('wp-login.php').to_s
|
||||
|
||||
# Let's check if the login url is redirected (to https url for example)
|
||||
if redirection = redirection(@login_url)
|
||||
@login_url = redirection
|
||||
end
|
||||
end
|
||||
|
||||
@login_url
|
||||
end
|
||||
|
||||
def redirection(url)
|
||||
redirection = nil
|
||||
response = Browser.get(url)
|
||||
|
||||
if response.code == 301 || response.code == 302
|
||||
redirection = response.headers_hash['location']
|
||||
|
||||
# Let's check if there is a redirection in the redirection
|
||||
if other_redirection = redirection(redirection)
|
||||
redirection = other_redirection
|
||||
end
|
||||
end
|
||||
|
||||
redirection
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def to_s
|
||||
s = "#{id}"
|
||||
s << " | #{login}" if login
|
||||
s << " | #{display_name}" if display_name
|
||||
s
|
||||
end
|
||||
|
||||
# @param [ WpUser ] other
|
||||
def <=>(other)
|
||||
id <=> other.id
|
||||
end
|
||||
|
||||
# @param [ WpUser ] other
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
def ==(other)
|
||||
self === other
|
||||
end
|
||||
|
||||
# @param [ WpUser ] other
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
def ===(other)
|
||||
id === other.id && login === other.login
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
@@ -25,16 +25,16 @@ class WpUser < WpItem
|
||||
hydra = browser.hydra
|
||||
queue_count = 0
|
||||
found = false
|
||||
progress_bar = self.progress_bar(count_file_lines(wordlist), options)
|
||||
progress_bar = self.progress_bar(count_file_lines(wordlist)+1, options)
|
||||
|
||||
File.open(wordlist).each do |password|
|
||||
password.chop!
|
||||
password.chomp!
|
||||
|
||||
# A successfull login will redirect us to the redirect_to parameter
|
||||
# Generate a random one on each request
|
||||
unless redirect_url
|
||||
random = (0...8).map { 65.+(rand(26)).chr }.join
|
||||
redirect_url = "#@uri#{random}/"
|
||||
redirect_url = "#{@uri}#{random}/"
|
||||
end
|
||||
|
||||
request = login_request(password, redirect_url)
|
||||
@@ -63,9 +63,10 @@ class WpUser < WpItem
|
||||
|
||||
# run all of the remaining requests
|
||||
hydra.run
|
||||
puts if options[:show_progression] # mandatory to avoid the output of the progressbar to be overriden
|
||||
end
|
||||
|
||||
# @param [ Integer ] targets_size
|
||||
# @param [ Integer ] passwords_size
|
||||
# @param [ Hash ] options
|
||||
#
|
||||
# @return [ ProgressBar ]
|
||||
@@ -108,13 +109,13 @@ class WpUser < WpItem
|
||||
elsif response.body =~ /login_error/i
|
||||
verbose = "\n Incorrect login and/or password."
|
||||
elsif response.timed_out?
|
||||
progression = "#{critical('ERROR:')} Request timed out."
|
||||
progression = critical('ERROR: Request timed out.')
|
||||
elsif response.code == 0
|
||||
progression = "#{critical('ERROR:')} No response from remote server. WAF/IPS?"
|
||||
progression = critical("ERROR: No response from remote server. WAF/IPS? (#{response.return_message})")
|
||||
elsif response.code.to_s =~ /^50/
|
||||
progression = "#{critical('ERROR:')} Server error, try reducing the number of threads."
|
||||
progression = critical('ERROR: Server error, try reducing the number of threads.')
|
||||
else
|
||||
progression = "#{critical('ERROR:')} We received an unknown response for #{password}..."
|
||||
progression = critical("ERROR: We received an unknown response for #{password}...")
|
||||
verbose = critical(" Code: #{response.code}\n Body: #{response.body}\n")
|
||||
end
|
||||
|
||||
|
||||
@@ -39,7 +39,9 @@ class WpUser < WpItem
|
||||
#
|
||||
# @return [ String ] The login
|
||||
def self.login_from_author_pattern(text)
|
||||
text[%r{/author/([^/\b]+)/?}i, 1]
|
||||
return unless text =~ %r{/author/([^/\b"']+)/?}i
|
||||
|
||||
Regexp.last_match[1].force_encoding('UTF-8')
|
||||
end
|
||||
|
||||
# @param [ String ] body
|
||||
@@ -51,7 +53,8 @@ class WpUser < WpItem
|
||||
|
||||
unless login
|
||||
# No Permalinks
|
||||
login = body[%r{<body class="archive author author-([^\s]+) author-(\d+)}i, 1]
|
||||
login = body[%r{<body class="archive author author-([^\s]+)[ "]}i, 1]
|
||||
login ? login.force_encoding('UTF-8') : nil
|
||||
end
|
||||
|
||||
login
|
||||
|
||||
@@ -1,21 +1,27 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
require 'wp_version/findable'
|
||||
require 'wp_version/vulnerable'
|
||||
require 'wp_version/output'
|
||||
|
||||
class WpVersion < WpItem
|
||||
|
||||
extend WpVersion::Findable
|
||||
include WpVersion::Vulnerable
|
||||
include WpVersion::Output
|
||||
|
||||
# The version number
|
||||
attr_accessor :number
|
||||
alias_method :version, :number # Needed to have the right behaviour in Vulnerable#vulnerable_to?
|
||||
|
||||
# @return [ Array ]
|
||||
def allowed_options; super << :number << :found_from end
|
||||
|
||||
def identifier
|
||||
@identifier ||= number
|
||||
end
|
||||
|
||||
def db_file
|
||||
@db_file ||= WORDPRESSES_FILE
|
||||
end
|
||||
|
||||
# @param [ WpVersion ] other
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
@@ -23,4 +29,10 @@ class WpVersion < WpItem
|
||||
number == other.number
|
||||
end
|
||||
|
||||
# @return [ Array<String> ] All the stable versions from version_file
|
||||
def self.all(versions_file = WP_VERSIONS_FILE)
|
||||
Nokogiri.XML(File.open(versions_file)).css('version').reduce([]) do |a, node|
|
||||
a << node.text.to_s
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -1,218 +1,222 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpVersion < WpItem
|
||||
|
||||
module Findable
|
||||
|
||||
# Find the version of the blog designated from target_uri
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
# @param [ String ] wp_content_dir
|
||||
# @param [ String ] wp_plugins_dir
|
||||
#
|
||||
# @return [ WpVersion ]
|
||||
def find(target_uri, wp_content_dir, wp_plugins_dir, versions_xml)
|
||||
methods.grep(/^find_from_/).each do |method|
|
||||
|
||||
if method === :find_from_advanced_fingerprinting
|
||||
version = send(method, target_uri, wp_content_dir, wp_plugins_dir, versions_xml)
|
||||
else
|
||||
version = send(method, target_uri)
|
||||
end
|
||||
|
||||
if version
|
||||
return new(target_uri, number: version, found_from: method)
|
||||
end
|
||||
end
|
||||
nil
|
||||
end
|
||||
|
||||
# Used to check if the version is correct: must contain at least one dot.
|
||||
#
|
||||
# @return [ String ]
|
||||
def version_pattern
|
||||
'([^\r\n"\']+\.[^\r\n"\']+)'
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
# Returns the first match of <pattern> in the body of the url
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
# @param [ Regex ] pattern
|
||||
# @param [ String ] path
|
||||
#
|
||||
# @return [ String ]
|
||||
def scan_url(target_uri, pattern, path = nil)
|
||||
url = path ? target_uri.merge(path).to_s : target_uri.to_s
|
||||
response = Browser.get_and_follow_location(url)
|
||||
|
||||
response.body[pattern, 1]
|
||||
end
|
||||
|
||||
#
|
||||
# DO NOT Change the order of the following methods
|
||||
# unless you know what you are doing
|
||||
# See WpVersion.find
|
||||
#
|
||||
|
||||
# Attempts to find the wordpress version from,
|
||||
# the generator meta tag in the html source.
|
||||
#
|
||||
# The meta tag can be removed however it seems,
|
||||
# that it is reinstated on upgrade.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_meta_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{name="generator" content="wordpress #{version_pattern}"}i
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from,
|
||||
# the generator tag in the RSS feed source.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_rss_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{<generator>http://wordpress.org/\?v=#{version_pattern}</generator>}i,
|
||||
'feed/'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find WordPress version from,
|
||||
# the generator tag in the RDF feed source.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_rdf_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{<admin:generatorAgent rdf:resource="http://wordpress.org/\?v=#{version_pattern}" />}i,
|
||||
'feed/rdf/'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from,
|
||||
# the generator tag in the RSS2 feed source.
|
||||
#
|
||||
# Have not been able to find an example of this - Ryan
|
||||
#def find_from_rss2_generator(target_uri)
|
||||
# scan_url(
|
||||
# target_uri,
|
||||
# %r{<generator>http://wordpress.org/?v=(#{WpVersion.version_pattern})</generator>}i,
|
||||
# 'feed/rss/'
|
||||
# )
|
||||
#end
|
||||
|
||||
# Attempts to find the WordPress version from,
|
||||
# the generator tag in the Atom source.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_atom_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{<generator uri="http://wordpress.org/" version="#{version_pattern}">WordPress</generator>}i,
|
||||
'feed/atom/'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from,
|
||||
# the generator tag in the comment rss source.
|
||||
#
|
||||
# Have not been able to find an example of this - Ryan
|
||||
#def find_from_comments_rss_generator(target_uri)
|
||||
# scan_url(
|
||||
# target_uri,
|
||||
# %r{<!-- generator="WordPress/#{WpVersion.version_pattern}" -->}i,
|
||||
# 'comments/feed/'
|
||||
# )
|
||||
#end
|
||||
|
||||
# Uses data/wp_versions.xml to try to identify a
|
||||
# wordpress version.
|
||||
#
|
||||
# It does this by using client side file hashing
|
||||
#
|
||||
# /!\ Warning : this method might return false positive if the file used for fingerprinting is part of a theme (they can be updated)
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
# @param [ String ] wp_content_dir
|
||||
# @param [ String ] wp_plugins_dir
|
||||
# @param [ String ] versions_xml The path to the xml containing all versions
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_advanced_fingerprinting(target_uri, wp_content_dir, wp_plugins_dir, versions_xml)
|
||||
xml = xml(versions_xml)
|
||||
|
||||
# This wp_item will take care of encoding the path
|
||||
# and replace variables like $wp-content$ & $wp-plugins$
|
||||
wp_item = WpItem.new(target_uri,
|
||||
wp_content_dir: wp_content_dir,
|
||||
wp_plugins_dir: wp_plugins_dir)
|
||||
|
||||
xml.xpath('//file').each do |node|
|
||||
wp_item.path = node.attribute('src').text
|
||||
|
||||
response = Browser.get(wp_item.url)
|
||||
md5sum = Digest::MD5.hexdigest(response.body)
|
||||
|
||||
node.search('hash').each do |hash|
|
||||
if hash.attribute('md5').text == md5sum
|
||||
return hash.search('version').text
|
||||
end
|
||||
end
|
||||
end
|
||||
nil
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from the readme.html file.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_readme(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{<br />\sversion #{version_pattern}}i,
|
||||
'readme.html'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from the sitemap.xml file.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_sitemap_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{generator="wordpress/#{version_pattern}"}i,
|
||||
'sitemap.xml'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from the p-links-opml.php file.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_links_opml(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{generator="wordpress/#{version_pattern}"}i,
|
||||
'wp-links-opml.php'
|
||||
)
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpVersion < WpItem
|
||||
|
||||
module Findable
|
||||
|
||||
# Find the version of the blog designated from target_uri
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
# @param [ String ] wp_content_dir
|
||||
# @param [ String ] wp_plugins_dir
|
||||
#
|
||||
# @return [ WpVersion ]
|
||||
def find(target_uri, wp_content_dir, wp_plugins_dir, versions_xml)
|
||||
methods.grep(/^find_from_/).each do |method|
|
||||
|
||||
if method === :find_from_advanced_fingerprinting
|
||||
version = send(method, target_uri, wp_content_dir, wp_plugins_dir, versions_xml)
|
||||
else
|
||||
version = send(method, target_uri)
|
||||
end
|
||||
|
||||
if version
|
||||
return new(target_uri, number: version, found_from: method)
|
||||
end
|
||||
end
|
||||
nil
|
||||
end
|
||||
|
||||
# Used to check if the version is correct: must contain at least one dot.
|
||||
#
|
||||
# @return [ String ]
|
||||
def version_pattern
|
||||
'([^\r\n"\',]+\.[^\r\n"\',]+)'
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
# Returns the first match of <pattern> in the body of the url
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
# @param [ Regex ] pattern
|
||||
# @param [ String ] path
|
||||
#
|
||||
# @return [ String ]
|
||||
def scan_url(target_uri, pattern, path = nil)
|
||||
url = path ? target_uri.merge(path).to_s : target_uri.to_s
|
||||
response = Browser.get_and_follow_location(url)
|
||||
|
||||
response.body[pattern, 1]
|
||||
end
|
||||
|
||||
#
|
||||
# DO NOT Change the order of the following methods
|
||||
# unless you know what you are doing
|
||||
# See WpVersion.find
|
||||
#
|
||||
|
||||
# Attempts to find the wordpress version from,
|
||||
# the generator meta tag in the html source.
|
||||
#
|
||||
# The meta tag can be removed however it seems,
|
||||
# that it is reinstated on upgrade.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_meta_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{name="generator" content="wordpress #{version_pattern}.*"}i
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from,
|
||||
# the generator tag in the RSS feed source.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_rss_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{<generator>http://wordpress.org/\?v=#{version_pattern}</generator>}i,
|
||||
'feed/'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find WordPress version from,
|
||||
# the generator tag in the RDF feed source.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_rdf_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{<admin:generatorAgent rdf:resource="http://wordpress.org/\?v=#{version_pattern}" />}i,
|
||||
'feed/rdf/'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from,
|
||||
# the generator tag in the Atom source.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_atom_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{<generator uri="http://wordpress.org/" version="#{version_pattern}">WordPress</generator>}i,
|
||||
'feed/atom/'
|
||||
)
|
||||
end
|
||||
|
||||
def find_from_stylesheets_numbers(target_uri)
|
||||
wp_versions = WpVersion.all
|
||||
found = {}
|
||||
pattern = /\bver=([0-9\.]+)/i
|
||||
|
||||
Nokogiri::HTML(Browser.get(target_uri.to_s).body).css('link,script').each do |tag|
|
||||
%w(href src).each do |attribute|
|
||||
attr_value = tag.attribute(attribute).to_s
|
||||
|
||||
next if attr_value.nil? || attr_value.empty?
|
||||
|
||||
uri = Addressable::URI.parse(attr_value)
|
||||
next unless uri.query && uri.query.match(pattern)
|
||||
|
||||
version = Regexp.last_match[1].to_s
|
||||
|
||||
found[version] ||= 0
|
||||
found[version] += 1
|
||||
end
|
||||
end
|
||||
|
||||
found.delete_if { |v, _| !wp_versions.include?(v) }
|
||||
|
||||
best_guess = found.sort_by(&:last).last
|
||||
# best_guess[0]: version number, [1] numbers of occurences
|
||||
best_guess && best_guess[1] > 1 ? best_guess[0] : nil
|
||||
end
|
||||
|
||||
# Uses data/wp_versions.xml to try to identify a
|
||||
# wordpress version.
|
||||
#
|
||||
# It does this by using client side file hashing
|
||||
#
|
||||
# /!\ Warning : this method might return false positive if the file used for fingerprinting is part of a theme (they can be updated)
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
# @param [ String ] wp_content_dir
|
||||
# @param [ String ] wp_plugins_dir
|
||||
# @param [ String ] versions_xml The path to the xml containing all versions
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_advanced_fingerprinting(target_uri, wp_content_dir, wp_plugins_dir, versions_xml)
|
||||
xml = xml(versions_xml)
|
||||
|
||||
# This wp_item will take care of encoding the path
|
||||
# and replace variables like $wp-content$ & $wp-plugins$
|
||||
wp_item = WpItem.new(target_uri,
|
||||
wp_content_dir: wp_content_dir,
|
||||
wp_plugins_dir: wp_plugins_dir)
|
||||
|
||||
xml.xpath('//file').each do |node|
|
||||
wp_item.path = node.attribute('src').text
|
||||
|
||||
response = Browser.get(wp_item.url)
|
||||
md5sum = Digest::MD5.hexdigest(response.body)
|
||||
|
||||
node.search('hash').each do |hash|
|
||||
if hash.attribute('md5').text == md5sum
|
||||
return hash.search('version').text
|
||||
end
|
||||
end
|
||||
end
|
||||
nil
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from the readme.html file.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_readme(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{<br />\sversion #{version_pattern}}i,
|
||||
'readme.html'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from the sitemap.xml file.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_sitemap_generator(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{generator="wordpress/#{version_pattern}"}i,
|
||||
'sitemap.xml'
|
||||
)
|
||||
end
|
||||
|
||||
# Attempts to find the WordPress version from the p-links-opml.php file.
|
||||
#
|
||||
# @param [ URI ] target_uri
|
||||
#
|
||||
# @return [ String ] The version number
|
||||
def find_from_links_opml(target_uri)
|
||||
scan_url(
|
||||
target_uri,
|
||||
%r{generator="wordpress/#{version_pattern}"}i,
|
||||
'wp-links-opml.php'
|
||||
)
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
@@ -5,13 +5,16 @@ class WpVersion < WpItem
|
||||
|
||||
def output(verbose = false)
|
||||
puts
|
||||
puts "#{info('[+]')} WordPress version #{self.number} identified from #{self.found_from}"
|
||||
puts info("WordPress version #{self.number} identified from #{self.found_from}")
|
||||
|
||||
vulnerabilities = self.vulnerabilities
|
||||
|
||||
unless vulnerabilities.empty?
|
||||
puts "#{critical('[!]')} #{vulnerabilities.size} vulnerabilities identified from the version number"
|
||||
|
||||
if vulnerabilities.size == 1
|
||||
puts critical("#{vulnerabilities.size} vulnerability identified from the version number")
|
||||
else
|
||||
puts critical("#{vulnerabilities.size} vulnerabilities identified from the version number")
|
||||
end
|
||||
vulnerabilities.output
|
||||
end
|
||||
end
|
||||
|
||||
@@ -1,25 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpVersion < WpItem
|
||||
module Vulnerable
|
||||
|
||||
# @return [ String ] The path to the file containing vulnerabilities
|
||||
def vulns_file
|
||||
unless @vulns_file
|
||||
@vulns_file = WP_VULNS_FILE
|
||||
end
|
||||
@vulns_file
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def identifier
|
||||
@number
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
# def vulns_xpath
|
||||
# "//wordpress[@version='#{@number}']/vulnerability"
|
||||
# end
|
||||
|
||||
end
|
||||
end
|
||||
@@ -11,8 +11,8 @@ class VersionCompare
|
||||
# @return [ Boolean ]
|
||||
def self.lesser_or_equal?(version1, version2)
|
||||
# Prepend a '0' if the version starts with a '.'
|
||||
version1 = "0#{version1}" if version1 && version1[0,1] == '.'
|
||||
version2 = "0#{version2}" if version2 && version2[0,1] == '.'
|
||||
version1 = prepend_zero(version1)
|
||||
version2 = prepend_zero(version2)
|
||||
|
||||
return true if (version1 == version2)
|
||||
# Both versions must be set
|
||||
@@ -27,4 +27,36 @@ class VersionCompare
|
||||
end
|
||||
return false
|
||||
end
|
||||
|
||||
# Compares two version strings. Returns true if version1 < version2
|
||||
# and false otherwise
|
||||
#
|
||||
# @param [ String ] version1
|
||||
# @param [ String ] version2
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
def self.lesser?(version1, version2)
|
||||
# Prepend a '0' if the version starts with a '.'
|
||||
version1 = prepend_zero(version1)
|
||||
version2 = prepend_zero(version2)
|
||||
|
||||
return false if (version1 == version2)
|
||||
# Both versions must be set
|
||||
return false unless (version1 and version2)
|
||||
return false if (version1.empty? or version2.empty?)
|
||||
begin
|
||||
return true if (Gem::Version.new(version1) < Gem::Version.new(version2))
|
||||
rescue ArgumentError => e
|
||||
# Example: ArgumentError: Malformed version number string a
|
||||
return false if e.message =~ /Malformed version number string/
|
||||
raise
|
||||
end
|
||||
return false
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def self.prepend_zero(version)
|
||||
return nil if version.nil?
|
||||
version[0,1] == '.' ? "0#{version}" : version
|
||||
end
|
||||
end
|
||||
|
||||
@@ -31,10 +31,11 @@ begin
|
||||
require 'pathname'
|
||||
# Third party libs
|
||||
require 'typhoeus'
|
||||
require 'json'
|
||||
require 'yajl/json_gem'
|
||||
require 'nokogiri'
|
||||
require 'terminal-table'
|
||||
require 'ruby-progressbar'
|
||||
require 'addressable/uri'
|
||||
# Custom libs
|
||||
require 'common/browser'
|
||||
require 'common/custom_option_parser'
|
||||
|
||||
@@ -54,10 +54,9 @@ class WebSite
|
||||
|
||||
redirected_uri = URI.parse(add_trailing_slash(add_http_protocol(url)))
|
||||
if response.code == 301 || response.code == 302
|
||||
redirection = response.headers_hash['location']
|
||||
if redirection[0] == '/'
|
||||
redirection = "#{redirected_uri.scheme}://#{redirected_uri.host}#{redirection}"
|
||||
end
|
||||
redirection = redirected_uri.merge(response.headers_hash['location']).to_s
|
||||
|
||||
return redirection if url == redirection # prevents infinite loop
|
||||
|
||||
# Let's check if there is a redirection in the redirection
|
||||
if other_redirection = redirection(redirection)
|
||||
|
||||
@@ -15,7 +15,6 @@ class WebSite
|
||||
@uri.clone.merge('robots.txt').to_s
|
||||
end
|
||||
|
||||
|
||||
# Parse robots.txt
|
||||
# @return [ Array ] URLs generated from robots.txt
|
||||
def parse_robots_txt
|
||||
@@ -29,6 +28,7 @@ class WebSite
|
||||
if entries
|
||||
entries.flatten!
|
||||
entries.compact.sort!
|
||||
entries.uniq!
|
||||
wordpress_path = @uri.path
|
||||
RobotsTxt.known_dirs.each do |d|
|
||||
entries.delete(d)
|
||||
@@ -40,9 +40,9 @@ class WebSite
|
||||
entries.each do |d|
|
||||
begin
|
||||
temp = @uri.clone
|
||||
temp.path = d
|
||||
temp.path = d.strip
|
||||
rescue URI::Error
|
||||
temp = d
|
||||
temp = d.strip
|
||||
end
|
||||
return_object << temp.to_s
|
||||
end
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
require 'web_site'
|
||||
require 'wp_target/malwares'
|
||||
require 'wp_target/wp_readme'
|
||||
require 'wp_target/wp_registrable'
|
||||
require 'wp_target/wp_config_backup'
|
||||
@@ -11,7 +10,6 @@ require 'wp_target/wp_custom_directories'
|
||||
require 'wp_target/wp_full_path_disclosure'
|
||||
|
||||
class WpTarget < WebSite
|
||||
include WpTarget::Malwares
|
||||
include WpTarget::WpReadme
|
||||
include WpTarget::WpRegistrable
|
||||
include WpTarget::WpConfigBackup
|
||||
@@ -23,14 +21,20 @@ class WpTarget < WebSite
|
||||
attr_reader :verbose
|
||||
|
||||
def initialize(target_url, options = {})
|
||||
raise Exception.new('target_url can not be nil or empty') if target_url.nil? || target_url == ''
|
||||
super(target_url)
|
||||
|
||||
@verbose = options[:verbose]
|
||||
@wp_content_dir = options[:wp_content_dir]
|
||||
@wp_plugins_dir = options[:wp_plugins_dir]
|
||||
@multisite = nil
|
||||
@vhost = options[:vhost]
|
||||
|
||||
Browser.instance.referer = url
|
||||
if @vhost
|
||||
Browser.instance.vhost = @vhost
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
# check if the target website is
|
||||
@@ -42,10 +46,12 @@ class WpTarget < WebSite
|
||||
|
||||
# Note: in the future major WPScan version, change the user-agent to see
|
||||
# if the response is a 200 ?
|
||||
fail "The target is responding with a 403, this might be due to a WAF or a plugin\n" \
|
||||
'You should try to supply a valid user-agent via the --user-agent option' if response.code == 403
|
||||
fail "The target is responding with a 403, this might be due to a WAF or a plugin.\n" \
|
||||
'You should try to supply a valid user-agent via the --user-agent option or use the --random-agent option' if response.code == 403
|
||||
|
||||
if response.body =~ /["'][^"']*\/wp-content\/[^"']*["']/i
|
||||
dir = wp_content_dir ? wp_content_dir : 'wp-content'
|
||||
|
||||
if response.body =~ /["'][^"']*\/#{Regexp.escape(dir)}\/[^"']*["']/i
|
||||
wordpress = true
|
||||
else
|
||||
|
||||
@@ -72,9 +78,7 @@ class WpTarget < WebSite
|
||||
|
||||
# Let's check if the login url is redirected (to https url for example)
|
||||
redirection = redirection(url)
|
||||
if redirection
|
||||
url = redirection
|
||||
end
|
||||
url = redirection if redirection
|
||||
|
||||
url
|
||||
end
|
||||
|
||||
@@ -1,50 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpTarget < WebSite
|
||||
module Malwares
|
||||
# Used as cache :
|
||||
# nil => malwares not checked,
|
||||
# [] => no malwares,
|
||||
# otherwise array of malwares url found
|
||||
@malwares = nil
|
||||
|
||||
def has_malwares?(malwares_file_path = nil)
|
||||
!malwares(malwares_file_path).empty?
|
||||
end
|
||||
|
||||
# return array of string (url of malwares found)
|
||||
def malwares(malwares_file_path = nil)
|
||||
unless @malwares
|
||||
malwares_found = []
|
||||
malwares_file = Malwares.malwares_file(malwares_file_path)
|
||||
index_page_body = Browser.get(@uri.to_s).body
|
||||
|
||||
File.open(malwares_file, 'r') do |file|
|
||||
file.readlines.collect do |url|
|
||||
chomped_url = url.chomp
|
||||
|
||||
if chomped_url.length > 0
|
||||
malwares_found += index_page_body.scan(Malwares.malware_pattern(chomped_url))
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
malwares_found.flatten!
|
||||
malwares_found.uniq!
|
||||
|
||||
@malwares = malwares_found
|
||||
end
|
||||
@malwares
|
||||
end
|
||||
|
||||
def self.malwares_file(malwares_file_path)
|
||||
malwares_file_path || DATA_DIR + '/malwares.txt'
|
||||
end
|
||||
|
||||
def self.malware_pattern(url_regex)
|
||||
# no need to escape regex here, because malware.txt contains regex
|
||||
%r{<(?:script|iframe).* src=(?:"|')(#{url_regex}[^"']*)(?:"|')[^>]*>}i
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
@@ -40,7 +40,7 @@ class WpTarget < WebSite
|
||||
# @return [ Array ]
|
||||
def self.config_backup_files
|
||||
%w{
|
||||
wp-config.php~ #wp-config.php# wp-config.php.save .wp-config.php.swp wp-config.php.swp wp-config.php.swo
|
||||
wp-config.php~ #wp-config.php# wp-config.php.save .wp-config.php.swp wp-config.php.swp wp-config.php.swo
|
||||
wp-config.php_bak wp-config.bak wp-config.php.bak wp-config.save wp-config.old wp-config.php.old
|
||||
wp-config.php.orig wp-config.orig wp-config.php.original wp-config.original wp-config.txt
|
||||
} # thanks to Feross.org for these
|
||||
|
||||
@@ -23,9 +23,9 @@ class WpTarget < WebSite
|
||||
# @return [ Boolean ]
|
||||
def default_wp_content_dir_exists?
|
||||
response = Browser.get(@uri.merge('wp-content').to_s)
|
||||
hash = Digest::MD5.hexdigest(response.body)
|
||||
|
||||
if WpTarget.valid_response_codes.include?(response.code)
|
||||
hash = WebSite.page_hash(response)
|
||||
return true if hash != error_404_hash and hash != homepage_hash
|
||||
end
|
||||
|
||||
|
||||
@@ -2,19 +2,21 @@
|
||||
|
||||
class WpTarget < WebSite
|
||||
module WpFullPathDisclosure
|
||||
|
||||
# Check for Full Path Disclosure (FPD)
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
def has_full_path_disclosure?
|
||||
response = Browser.get(full_path_disclosure_url())
|
||||
response.body[%r{Fatal error}i] ? true : false
|
||||
Browser.get(full_path_disclosure_url).body[%r/Fatal error/i] ? true : false
|
||||
end
|
||||
|
||||
def full_path_disclosure_data
|
||||
return nil unless has_full_path_disclosure?
|
||||
Browser.get(full_path_disclosure_url).body[/Fatal error:.+? in (.+?) on/i, 1]
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def full_path_disclosure_url
|
||||
@uri.merge('wp-includes/rss-functions.php').to_s
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
@@ -8,7 +8,7 @@ class WpTarget < WebSite
|
||||
@login_protection_plugin = nil
|
||||
|
||||
def has_login_protection?
|
||||
!login_protection_plugin().nil?
|
||||
!login_protection_plugin.nil?
|
||||
end
|
||||
|
||||
# Checks if a login protection plugin is enabled
|
||||
@@ -74,7 +74,7 @@ class WpTarget < WebSite
|
||||
|
||||
# http://wordpress.org/extend/plugins/login-security-solution/
|
||||
def has_login_security_solution_protection?
|
||||
Browser.get(login_security_solution_url()).code != 404
|
||||
Browser.get(login_security_solution_url).code != 404
|
||||
end
|
||||
|
||||
def login_security_solution_url
|
||||
@@ -99,5 +99,12 @@ class WpTarget < WebSite
|
||||
plugin_url('bluetrait-event-viewer')
|
||||
end
|
||||
|
||||
# https://wordpress.org/plugins/security-protection/
|
||||
def has_security_protection_protection?
|
||||
Nokogiri::HTML(Browser.get(login_url).body).css('script').each do |node|
|
||||
return true if node['src'] =~ /security-protection.js/i
|
||||
end
|
||||
false
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -2,15 +2,14 @@
|
||||
|
||||
class WpTarget < WebSite
|
||||
module WpMustUsePlugins
|
||||
|
||||
# Checks to see if the must use plugin folder exists
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
def has_must_use_plugins?
|
||||
response = Browser.get(must_use_url)
|
||||
|
||||
if response && WpTarget.valid_response_codes.include?(response.code)
|
||||
hash = WebSite.page_hash(response.body)
|
||||
if response && [200, 401, 403].include?(response.code)
|
||||
hash = WebSite.page_hash(response)
|
||||
return true if hash != error_404_hash && hash != homepage_hash
|
||||
end
|
||||
|
||||
@@ -21,6 +20,5 @@ class WpTarget < WebSite
|
||||
def must_use_url
|
||||
@uri.merge("#{wp_content_dir}/mu-plugins/").to_s
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
@@ -10,7 +10,7 @@ class WpTarget < WebSite
|
||||
#
|
||||
# @return [ Boolean ]
|
||||
def has_readme?
|
||||
response = Browser.get(readme_url())
|
||||
response = Browser.get(readme_url)
|
||||
|
||||
unless response.code == 404
|
||||
return response.body =~ %r{wordpress}i ? true : false
|
||||
|
||||
@@ -97,22 +97,36 @@ def help
|
||||
puts ' If no protocol is given (format host:port), HTTP will be used.'
|
||||
puts '--proxy-auth <username:password> Supply the proxy login credentials.'
|
||||
puts '--basic-auth <username:password> Set the HTTP Basic authentication.'
|
||||
puts '--wordlist | -w <wordlist> Supply a wordlist for the password bruter and do the brute.'
|
||||
puts '--wordlist | -w <wordlist> Supply a wordlist for the password brute forcer.'
|
||||
puts '--username | -U <username> Only brute force the supplied username.'
|
||||
puts '--usernames <path-to-file> Only brute force the usernames from the file.'
|
||||
puts '--threads | -t <number of threads> The number of threads to use when multi-threading requests.'
|
||||
puts '--cache-ttl <cache-ttl> Typhoeus cache TTL.'
|
||||
puts '--request-timeout <request-timeout> Request Timeout.'
|
||||
puts '--connect-timeout <connect-timeout> Connect Timeout.'
|
||||
puts '--max-threads <max-threads> Maximum Threads.'
|
||||
puts '--throttle <milliseconds> Milliseconds to wait before doing another web request. If used, the --threads should be set to 1.'
|
||||
puts '--help | -h This help screen.'
|
||||
puts '--verbose | -v Verbose output.'
|
||||
puts '--version Output the current version and exit.'
|
||||
puts
|
||||
end
|
||||
|
||||
# Hook to check if the target if down during the scan
|
||||
# The target is considered down after 10 requests with status = 0
|
||||
down = 0
|
||||
# And have the number of requests performed to display at the end of the scan
|
||||
# The target is considered down after 30 requests with status = 0
|
||||
down = 0
|
||||
@total_requests_done = 0
|
||||
|
||||
Typhoeus.on_complete do |response|
|
||||
next if response.cached?
|
||||
|
||||
down += 1 if response.code == 0
|
||||
fail 'The target seems to be down' if down >= 10
|
||||
@total_requests_done += 1
|
||||
|
||||
fail 'The target seems to be down' if down >= 30
|
||||
|
||||
next unless Browser.instance.throttle > 0
|
||||
|
||||
sleep(Browser.instance.throttle)
|
||||
end
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class WpscanOptions
|
||||
|
||||
ACCESSOR_OPTIONS = [
|
||||
:batch,
|
||||
:enumerate_plugins,
|
||||
@@ -14,15 +13,18 @@ class WpscanOptions
|
||||
:enumerate_usernames,
|
||||
:enumerate_usernames_range,
|
||||
:no_color,
|
||||
:log,
|
||||
:proxy,
|
||||
:proxy_auth,
|
||||
:threads,
|
||||
:url,
|
||||
:vhost,
|
||||
:wordlist,
|
||||
:force,
|
||||
:update,
|
||||
:verbose,
|
||||
:username,
|
||||
:usernames,
|
||||
:password,
|
||||
:follow_redirection,
|
||||
:wp_content_dir,
|
||||
@@ -39,7 +41,9 @@ class WpscanOptions
|
||||
:cache_ttl,
|
||||
:request_timeout,
|
||||
:connect_timeout,
|
||||
:max_threads
|
||||
:max_threads,
|
||||
:no_banner,
|
||||
:throttle
|
||||
]
|
||||
|
||||
attr_accessor *ACCESSOR_OPTIONS
|
||||
@@ -51,11 +55,17 @@ class WpscanOptions
|
||||
end
|
||||
|
||||
def url=(url)
|
||||
raise 'Empty URL given' if !url
|
||||
raise Exception.new('Empty URL given') if url.nil? || url == ''
|
||||
|
||||
url = Addressable::URI.parse(url).normalize.to_s unless url.ascii_only?
|
||||
|
||||
@url = URI.parse(add_http_protocol(url)).to_s
|
||||
end
|
||||
|
||||
def vhost=(vhost)
|
||||
@vhost = vhost
|
||||
end
|
||||
|
||||
def threads=(threads)
|
||||
@threads = threads.is_a?(Integer) ? threads : threads.to_i
|
||||
end
|
||||
@@ -68,6 +78,12 @@ class WpscanOptions
|
||||
end
|
||||
end
|
||||
|
||||
def usernames=(file)
|
||||
fail "The file #{file} does not exist" unless File.exists?(file)
|
||||
|
||||
@usernames = file
|
||||
end
|
||||
|
||||
def proxy=(proxy)
|
||||
if proxy.index(':') == nil
|
||||
raise 'Invalid proxy format. Should be host:port.'
|
||||
@@ -235,8 +251,10 @@ class WpscanOptions
|
||||
def self.get_opt_long
|
||||
GetoptLong.new(
|
||||
['--url', '-u', GetoptLong::REQUIRED_ARGUMENT],
|
||||
['--vhost',GetoptLong::OPTIONAL_ARGUMENT],
|
||||
['--enumerate', '-e', GetoptLong::OPTIONAL_ARGUMENT],
|
||||
['--username', '-U', GetoptLong::REQUIRED_ARGUMENT],
|
||||
['--usernames', GetoptLong::REQUIRED_ARGUMENT],
|
||||
['--wordlist', '-w', GetoptLong::REQUIRED_ARGUMENT],
|
||||
['--threads', '-t', GetoptLong::REQUIRED_ARGUMENT],
|
||||
['--force', '-f', GetoptLong::NO_ARGUMENT],
|
||||
@@ -261,7 +279,10 @@ class WpscanOptions
|
||||
['--max-threads', GetoptLong::REQUIRED_ARGUMENT],
|
||||
['--batch', GetoptLong::NO_ARGUMENT],
|
||||
['--no-color', GetoptLong::NO_ARGUMENT],
|
||||
['--cookie', GetoptLong::REQUIRED_ARGUMENT]
|
||||
['--cookie', GetoptLong::REQUIRED_ARGUMENT],
|
||||
['--log', GetoptLong::NO_ARGUMENT],
|
||||
['--no-banner', GetoptLong::NO_ARGUMENT],
|
||||
['--throttle', GetoptLong::REQUIRED_ARGUMENT]
|
||||
)
|
||||
end
|
||||
|
||||
|
||||
@@ -1,138 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class CheckerPlugin < Plugin
|
||||
|
||||
def initialize
|
||||
super(author: 'WPScanTeam - @erwanlr')
|
||||
|
||||
register_options(
|
||||
['--check-vuln-ref-urls', '--cvru', 'Check all the vulnerabilities reference urls for 404'],
|
||||
['--check-local-vulnerable-files LOCAL_DIRECTORY', '--clvf', 'Perform a recursive scan in the LOCAL_DIRECTORY to find vulnerable files or shells']
|
||||
)
|
||||
end
|
||||
|
||||
def run(options = {})
|
||||
if options[:check_vuln_ref_urls]
|
||||
check_vuln_ref_urls
|
||||
end
|
||||
|
||||
if options[:check_local_vulnerable_files]
|
||||
check_local_vulnerable_files(options[:check_local_vulnerable_files])
|
||||
end
|
||||
end
|
||||
|
||||
def check_vuln_ref_urls
|
||||
vuln_ref_files = [PLUGINS_VULNS_FILE, THEMES_VULNS_FILE, WP_VULNS_FILE]
|
||||
error_codes = [404, 500, 403]
|
||||
not_found_regexp = %r{No Results Found|error 404|ID Invalid or Not Found}i
|
||||
|
||||
puts '[+] Checking vulnerabilities reference urls'
|
||||
|
||||
vuln_ref_files.each do |vuln_ref_file|
|
||||
json = json(vuln_ref_file)
|
||||
|
||||
urls = []
|
||||
json.each do |asset|
|
||||
asset[asset.keys.inject]['vulnerabilities'].each do |url|
|
||||
unless url['url'].nil?
|
||||
url['url'].each do |url|
|
||||
urls << url
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
urls.uniq!
|
||||
|
||||
puts "[!] No URLs found in #{vuln_ref_file}!" if urls.empty?
|
||||
|
||||
dead_urls = []
|
||||
queue_count = 0
|
||||
request_count = 0
|
||||
browser = Browser.instance
|
||||
hydra = browser.hydra
|
||||
number_of_urls = urls.size
|
||||
|
||||
urls.each do |url|
|
||||
request = browser.forge_request(url, { cache_ttl: 0, followlocation: true })
|
||||
request_count += 1
|
||||
|
||||
request.on_complete do |response|
|
||||
print "\r [+] Checking #{vuln_ref_file} #{number_of_urls} total ... #{(request_count * 100) / number_of_urls}% complete."
|
||||
|
||||
if error_codes.include?(response.code) or not_found_regexp.match(response.body)
|
||||
dead_urls << url
|
||||
end
|
||||
end
|
||||
|
||||
hydra.queue(request)
|
||||
queue_count += 1
|
||||
|
||||
if queue_count == browser.max_threads
|
||||
hydra.run
|
||||
queue_count = 0
|
||||
end
|
||||
end
|
||||
|
||||
hydra.run
|
||||
puts
|
||||
unless dead_urls.empty?
|
||||
dead_urls.each { |url| puts " Not Found #{url}" }
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def check_local_vulnerable_files(dir_to_scan)
|
||||
if Dir.exist?(dir_to_scan)
|
||||
xml_file = LOCAL_FILES_FILE
|
||||
local_hashes = {}
|
||||
file_extension_to_scan = '*.{js,php,swf,html,htm}'
|
||||
|
||||
print '[+] Generating local hashes ... '
|
||||
|
||||
Dir[File.join(dir_to_scan, '**', file_extension_to_scan)]
|
||||
.select { |f| File.file?(f) }
|
||||
.each do |filename|
|
||||
sha1sum = Digest::SHA1.file(filename).hexdigest
|
||||
|
||||
if local_hashes.key?(sha1sum)
|
||||
local_hashes[sha1sum] << filename
|
||||
else
|
||||
local_hashes[sha1sum] = [filename]
|
||||
end
|
||||
end
|
||||
|
||||
puts 'done.'
|
||||
|
||||
puts '[+] Checking for vulnerable files ...'
|
||||
|
||||
xml = xml(xml_file)
|
||||
|
||||
xml.xpath('//hash').each do |node|
|
||||
sha1sum = node.attribute('sha1').text
|
||||
|
||||
if local_hashes.has_key?(sha1sum)
|
||||
local_filenames = local_hashes[sha1sum]
|
||||
vuln_title = node.search('title').text
|
||||
vuln_filename = node.search('file').text
|
||||
vuln_refrence = node.search('reference').text
|
||||
|
||||
puts " #{vuln_filename} found :"
|
||||
puts ' | Location(s):'
|
||||
local_filenames.each do |file|
|
||||
puts " | - #{file}"
|
||||
end
|
||||
puts ' |'
|
||||
puts " | Title: #{vuln_title}"
|
||||
puts " | Refrence: #{vuln_refrence}" if !vuln_refrence.empty?
|
||||
puts
|
||||
end
|
||||
end
|
||||
|
||||
puts 'done.'
|
||||
|
||||
else
|
||||
puts "The supplied directory '#{dir_to_scan}' does not exist"
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
@@ -1,91 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class CheckerSpelling < Plugin
|
||||
|
||||
def initialize
|
||||
super(author: 'WPScanTeam - @ethicalhack3r')
|
||||
|
||||
register_options(['--spellcheck', '--sc', 'Check all files for common spelling mistakes.'])
|
||||
end
|
||||
|
||||
def run(options = {})
|
||||
spellcheck if options[:spellcheck]
|
||||
end
|
||||
|
||||
def spellcheck
|
||||
mistakes = 0
|
||||
|
||||
puts '[+] Checking for spelling mistakes'
|
||||
puts
|
||||
|
||||
files.each do |file_name|
|
||||
if File.exists?(file_name)
|
||||
file = File.open(file_name, 'r')
|
||||
|
||||
misspellings.each_key do |misspelling|
|
||||
begin
|
||||
file.read.scan(/#{misspelling}/).each do |match|
|
||||
mistakes += 1
|
||||
puts "[MISSPELLING] File: #{file_name} Bad: #{match} Good: #{misspellings[misspelling]}"
|
||||
end
|
||||
rescue => e
|
||||
puts "Error in #{file_name} #{e}"
|
||||
next
|
||||
end
|
||||
end
|
||||
|
||||
file.close
|
||||
end
|
||||
end
|
||||
|
||||
puts
|
||||
puts "[+] Found #{mistakes} spelling mistakes"
|
||||
|
||||
mistakes
|
||||
end
|
||||
|
||||
def misspellings
|
||||
{
|
||||
/databse/i => 'database',
|
||||
/whith/i => 'with',
|
||||
/wich/i => 'which',
|
||||
/verions/i => 'versions',
|
||||
/vulnerabilitiy/i => 'vulnerability',
|
||||
/unkown/i => 'unknown',
|
||||
/recieved/i => 'received',
|
||||
/acheive/i => 'achieve',
|
||||
/wierd/i => 'weird',
|
||||
/untill/i => 'until',
|
||||
/alot/i => 'a lot',
|
||||
/randomstorm/ => 'RandomStorm',
|
||||
/wpscan/ => 'WPScan',
|
||||
/Wordpress/ => 'WordPress'
|
||||
}
|
||||
end
|
||||
|
||||
def files
|
||||
files = Dir['**/*'].reject {|fn| File.directory?(fn) }
|
||||
|
||||
ignore.each do |ignore|
|
||||
files.delete_if { |data| data.match(ignore) }
|
||||
end
|
||||
|
||||
files
|
||||
end
|
||||
|
||||
def ignore
|
||||
ignore = []
|
||||
|
||||
ignore << File.basename(__FILE__)
|
||||
ignore << 'spec/cache/'
|
||||
ignore << 'spec/spec_session/'
|
||||
ignore << 'cache/'
|
||||
ignore << 'coverage/'
|
||||
ignore << 'wordlist-iso-8859-1'
|
||||
ignore << 'log.txt'
|
||||
ignore << 'debug.log'
|
||||
ignore << 'wordlist.txt'
|
||||
|
||||
ignore
|
||||
end
|
||||
end
|
||||
@@ -1,106 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
class StatsPlugin < Plugin
|
||||
|
||||
def initialize
|
||||
super(author: 'WPScanTeam - Christian Mehlmauer')
|
||||
|
||||
register_options(
|
||||
['--stats', '-s', 'Show WpScan Database statistics.']
|
||||
)
|
||||
end
|
||||
|
||||
def run(options = {})
|
||||
if options[:stats]
|
||||
date_wp = File.mtime(WP_VULNS_FILE)
|
||||
date_plugins = File.mtime(PLUGINS_VULNS_FILE)
|
||||
date_themes = File.mtime(THEMES_VULNS_FILE)
|
||||
date_plugins_full = File.mtime(PLUGINS_FULL_FILE)
|
||||
date_themes_full = File.mtime(THEMES_FULL_FILE)
|
||||
|
||||
puts "WPScan Database Statistics:"
|
||||
puts "---------------------------"
|
||||
puts
|
||||
puts "[#] Total vulnerable versions: #{vuln_core_count}"
|
||||
puts "[#] Total vulnerable plugins: #{vuln_plugin_count}"
|
||||
puts "[#] Total vulnerable themes: #{vuln_theme_count}"
|
||||
puts
|
||||
puts "[#] Total version vulnerabilities: #{version_vulns_count}"
|
||||
puts "[#] Total fixed vulnerabilities: #{fix_version_count}"
|
||||
puts
|
||||
puts "[#] Total plugin vulnerabilities: #{plugin_vulns_count}"
|
||||
puts "[#] Total fixed vulnerabilities: #{fix_plugin_count}"
|
||||
puts
|
||||
puts "[#] Total theme vulnerabilities: #{theme_vulns_count}"
|
||||
puts "[#] Total fixed vulnerabilities: #{fix_theme_count}"
|
||||
puts
|
||||
puts "[#] Total plugins to enumerate: #{total_plugins}"
|
||||
puts "[#] Total themes to enumerate: #{total_themes}"
|
||||
puts
|
||||
puts "[+] WordPress DB modified: #{date_wp.strftime('%Y-%m-%d %H:%M:%S')}"
|
||||
puts "[+] Plugins DB modified: #{date_plugins.strftime('%Y-%m-%d %H:%M:%S')}"
|
||||
puts "[+] Themes DB modified: #{date_themes.strftime('%Y-%m-%d %H:%M:%S')}"
|
||||
puts "[+] Enumeration plugins: #{date_plugins_full.strftime('%Y-%m-%d %H:%M:%S')}"
|
||||
puts "[+] Enumeration themes: #{date_themes_full.strftime('%Y-%m-%d %H:%M:%S')}"
|
||||
puts
|
||||
puts "[+] Report generated: #{Time.now.strftime('%Y-%m-%d %H:%M:%S')}"
|
||||
end
|
||||
end
|
||||
|
||||
def vuln_core_count(file=WP_VULNS_FILE)
|
||||
json(file).size
|
||||
end
|
||||
|
||||
def vuln_plugin_count(file=PLUGINS_VULNS_FILE)
|
||||
json(file).size
|
||||
end
|
||||
|
||||
def vuln_theme_count(file=THEMES_VULNS_FILE)
|
||||
json(file).size
|
||||
end
|
||||
|
||||
def version_vulns_count(file=WP_VULNS_FILE)
|
||||
asset_vulns_count(json(file))
|
||||
end
|
||||
|
||||
def fix_version_count(file=WP_VULNS_FILE)
|
||||
asset_fixed_in_count(json(file))
|
||||
end
|
||||
|
||||
def plugin_vulns_count(file=PLUGINS_VULNS_FILE)
|
||||
asset_vulns_count(json(file))
|
||||
end
|
||||
|
||||
def fix_plugin_count(file=PLUGINS_VULNS_FILE)
|
||||
asset_fixed_in_count(json(file))
|
||||
end
|
||||
|
||||
def theme_vulns_count(file=THEMES_VULNS_FILE)
|
||||
asset_vulns_count(json(file))
|
||||
end
|
||||
|
||||
def fix_theme_count(file=THEMES_VULNS_FILE)
|
||||
asset_fixed_in_count(json(file))
|
||||
end
|
||||
|
||||
def total_plugins(file=PLUGINS_FULL_FILE)
|
||||
lines_in_file(file)
|
||||
end
|
||||
|
||||
def total_themes(file=THEMES_FULL_FILE)
|
||||
lines_in_file(file)
|
||||
end
|
||||
|
||||
def lines_in_file(file)
|
||||
IO.readlines(file).size
|
||||
end
|
||||
|
||||
def asset_vulns_count(json)
|
||||
json.map { |asset| asset[asset.keys.inject]['vulnerabilities'].size }.inject(:+)
|
||||
end
|
||||
|
||||
def asset_fixed_in_count(json)
|
||||
json.map { |asset| asset[asset.keys.inject]['vulnerabilities'].map {|a| a['fixed_in'].nil? ? 0 : 1 }.inject(:+) }.inject(:+)
|
||||
end
|
||||
|
||||
end
|
||||
@@ -1,20 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
require File.expand_path(File.dirname(__FILE__) + '/../common/common_helper')
|
||||
|
||||
require_files_from_directory(WPSTOOLS_LIB_DIR)
|
||||
require_files_from_directory(WPSTOOLS_PLUGINS_DIR, '**/*.rb')
|
||||
|
||||
def usage
|
||||
script_name = $0
|
||||
puts
|
||||
puts '-h for further help.'
|
||||
puts
|
||||
puts 'Examples:'
|
||||
puts
|
||||
puts 'Locally scan a wordpress installation for vulnerable files or shells'
|
||||
puts "ruby #{script_name} --check-local-vulnerable-files /var/www/wordpress/"
|
||||
puts
|
||||
puts 'See README for further information.'
|
||||
puts
|
||||
end
|
||||
@@ -64,7 +64,7 @@ describe Browser do
|
||||
|
||||
it 'raises an error' do
|
||||
File.symlink('./testfile', config_file)
|
||||
expect { browser.load_config(config_file) }.to raise_error("[ERROR] Config file is a symlink.")
|
||||
expect { browser.load_config(config_file) }.to raise_error('[ERROR] Config file is a symlink.')
|
||||
File.unlink(config_file)
|
||||
end
|
||||
end
|
||||
@@ -130,7 +130,7 @@ describe Browser do
|
||||
headers: { 'User-Agent' => 'SomeUA' },
|
||||
ssl_verifypeer: false, ssl_verifyhost: 0,
|
||||
cookiejar: cookie_jar, cookiefile: cookie_jar,
|
||||
timeout: 2000, connecttimeout: 1000,
|
||||
timeout: 60, connecttimeout: 10,
|
||||
maxredirs: 3,
|
||||
referer: nil
|
||||
}
|
||||
@@ -147,7 +147,6 @@ describe Browser do
|
||||
@expected = default_expectation
|
||||
end
|
||||
|
||||
|
||||
context 'when @proxy' do
|
||||
let(:proxy) { '127.0.0.1:9050' }
|
||||
let(:proxy_expectation) { default_expectation.merge(proxy: proxy) }
|
||||
@@ -166,11 +165,19 @@ describe Browser do
|
||||
end
|
||||
end
|
||||
|
||||
context 'when @request_timeout' do
|
||||
it 'gives an Integer' do
|
||||
browser.request_timeout = '10'
|
||||
|
||||
@expected = default_expectation.merge(timeout: 10)
|
||||
end
|
||||
end
|
||||
|
||||
context 'when @basic_auth' do
|
||||
it 'appends the basic_auth' do
|
||||
browser.basic_auth = 'user:pass'
|
||||
@expected = default_expectation.merge(
|
||||
headers: default_expectation[:headers].merge('Authorization' => 'Basic '+Base64.encode64('user:pass').chomp)
|
||||
headers: default_expectation[:headers].merge('Authorization' => 'Basic ' + Base64.encode64('user:pass').chomp)
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
@@ -30,14 +30,15 @@ describe CacheFileStore do
|
||||
|
||||
describe '#clean' do
|
||||
it "should remove all files from the cache dir (#{@cache_dir}" do
|
||||
# let's create some files into the directory first
|
||||
(0..5).each do |i|
|
||||
File.new(@cache.storage_path + "/file_#{i}.txt", File::CREAT)
|
||||
end
|
||||
|
||||
expect(count_files_in_dir(@cache.storage_path, 'file_*.txt')).to eq 6
|
||||
# clean is executed by other tests before
|
||||
before = count_files_in_dir(@cache.cache_dir)
|
||||
test_dir = File.expand_path("#{@cache.cache_dir}/test")
|
||||
Dir.mkdir test_dir
|
||||
#change the modification date
|
||||
%x[ touch -t 200701310846.26 #{test_dir} ]
|
||||
expect(count_files_in_dir(@cache.cache_dir)).to eq (before + 1)
|
||||
@cache.clean
|
||||
expect(count_files_in_dir(@cache.storage_path)).to eq 0
|
||||
expect(count_files_in_dir(@cache.cache_dir)).to eq before
|
||||
end
|
||||
end
|
||||
|
||||
@@ -91,7 +92,7 @@ describe CacheFileStore do
|
||||
it 'should create a unique storage dir' do
|
||||
storage_dirs = []
|
||||
|
||||
(1..5).each do |i|
|
||||
(1..5).each do |_|
|
||||
storage_dirs << CacheFileStore.new(cache_dir).storage_path
|
||||
end
|
||||
|
||||
|
||||
@@ -11,7 +11,7 @@ describe WpPlugins do
|
||||
let(:expected) do
|
||||
{
|
||||
request_params: { cache_ttl: 0, followlocation: true },
|
||||
vulns_file: PLUGINS_VULNS_FILE,
|
||||
vulns_file: PLUGINS_FILE,
|
||||
targets_items_from_file: [ WpPlugin.new(uri, name: 'plugin1'),
|
||||
WpPlugin.new(uri, name:'plugin-2'),
|
||||
WpPlugin.new(uri, name: 'mr-smith')],
|
||||
|
||||
@@ -13,7 +13,7 @@ describe WpThemes do
|
||||
let(:expected) do
|
||||
{
|
||||
request_params: { cache_ttl: 0, followlocation: true },
|
||||
vulns_file: THEMES_VULNS_FILE,
|
||||
vulns_file: THEMES_FILE,
|
||||
targets_items_from_file: [ WpTheme.new(uri, name: '3colours'),
|
||||
WpTheme.new(uri, name:'42k'),
|
||||
WpTheme.new(uri, name: 'a-ri')],
|
||||
|
||||
@@ -25,19 +25,19 @@ describe 'WpUsers::Output' do
|
||||
subject.push(@input)
|
||||
subject.flatten!
|
||||
subject.remove_junk_from_display_names
|
||||
expect(subject).to be === @expected
|
||||
expect(subject).to eq @expected
|
||||
end
|
||||
|
||||
it 'should return an empty array' do
|
||||
it 'returns an empty array' do
|
||||
@expected = @input
|
||||
end
|
||||
|
||||
it 'should return input object' do
|
||||
it 'returns input object' do
|
||||
@input.push(WpUser.new(nil))
|
||||
@expected = @input
|
||||
end
|
||||
|
||||
it 'should return input object' do
|
||||
it 'returns input object' do
|
||||
@input.push(WpUser.new(''))
|
||||
@expected = @input
|
||||
end
|
||||
@@ -50,23 +50,37 @@ describe 'WpUsers::Output' do
|
||||
@expected.push(WpUser.new('', login: '', id: 2, display_name: 'ijrjd'))
|
||||
end
|
||||
|
||||
it 'should return unmodified input object' do
|
||||
it 'returns unmodified input object' do
|
||||
@input.push(WpUser.new('', login: '', id: 1, display_name: 'lkjh asdfa'))
|
||||
@input.push(WpUser.new('', login: '', id: 2, display_name: 'ijrjd asdf'))
|
||||
@expected = @input
|
||||
end
|
||||
|
||||
it 'should return input object' do
|
||||
it 'returns input object' do
|
||||
@input.push(WpUser.new('', login: '', id: 1, display_name: 'lkjh asdf'))
|
||||
@expected = @input
|
||||
end
|
||||
|
||||
it 'should return an empty display_name' do
|
||||
it 'returns an empty display_name' do
|
||||
@input.push(WpUser.new('', login: '', id: 1, display_name: 'lkhj asdf'))
|
||||
@input.push(WpUser.new('', login: '', id: 2, display_name: 'lkhj asdf'))
|
||||
@expected = WpUsers.new(0)
|
||||
@expected.push(WpUser.new('', login: '', id: 1, display_name: ''))
|
||||
@expected.push(WpUser.new('', login: '', id: 2, display_name: ''))
|
||||
end
|
||||
|
||||
context 'when a user has no display_name' do
|
||||
it 'returns an empty display_name' do
|
||||
@input.push(WpUser.new('', login: '', id: 1, display_name: 'lkhj asdf'))
|
||||
@input.push(WpUser.new('', login: '', id: 2, display_name: 'lkhj asdf'))
|
||||
@input.push(WpUser.new('', login: '', id: 3))
|
||||
|
||||
@expected = WpUsers.new(0)
|
||||
|
||||
(1..3).each do |id|
|
||||
@expected.push(WpUser.new('', login: '', id: id, display_name: ''))
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -11,11 +11,11 @@ describe WpItem do
|
||||
end
|
||||
it_behaves_like 'WpItem::Versionable'
|
||||
it_behaves_like 'WpItem::Vulnerable' do
|
||||
let(:vulns_file) { MODELS_FIXTURES + '/wp_item/vulnerable/items_vulns.json' }
|
||||
let(:db_file) { MODELS_FIXTURES + '/wp_item/vulnerable/items_vulns.json' }
|
||||
let(:identifier) { 'neo' }
|
||||
let(:expected_refs) { {
|
||||
'id' => [2993],
|
||||
'url' => ['Ref 1,Ref 2'],
|
||||
'url' => ['Ref 1', 'Ref 2'],
|
||||
'cve' => ['2011-001'],
|
||||
'secunia' => ['secunia'],
|
||||
'osvdb' => ['osvdb'],
|
||||
|
||||
@@ -5,11 +5,11 @@ require 'spec_helper'
|
||||
describe WpPlugin do
|
||||
it_behaves_like 'WpPlugin::Vulnerable'
|
||||
it_behaves_like 'WpItem::Vulnerable' do
|
||||
let(:options) { { name: 'white-rabbit' } }
|
||||
let(:vulns_file) { MODELS_FIXTURES + '/wp_plugin/vulnerable/plugins_vulns.json' }
|
||||
let(:options) { { name: 'white-rabbit' } }
|
||||
let(:db_file) { MODELS_FIXTURES + '/wp_plugin/vulnerable/plugins.json' }
|
||||
let(:expected_refs) { {
|
||||
'id' => [2993],
|
||||
'url' => ['Ref 1,Ref 2'],
|
||||
'url' => ['Ref 1', 'Ref 2'],
|
||||
'cve' => ['2011-001'],
|
||||
'secunia' => ['secunia'],
|
||||
'osvdb' => ['osvdb'],
|
||||
|
||||
@@ -17,10 +17,9 @@ describe 'WpTheme::Findable' do
|
||||
|
||||
wp_theme = WpTheme.send(:find_from_css_link, uri)
|
||||
|
||||
if @expected
|
||||
expect(wp_theme).to be_a WpTheme
|
||||
end
|
||||
expect(wp_theme).to be_a WpTheme if @expected
|
||||
expect(wp_theme).to eq @expected
|
||||
expect(wp_theme.wp_content_dir).to eql 'wp-content' if @expected
|
||||
end
|
||||
|
||||
context 'when theme is not present' do
|
||||
@@ -59,6 +58,13 @@ describe 'WpTheme::Findable' do
|
||||
end
|
||||
end
|
||||
|
||||
# This one might introduce FP btw
|
||||
context 'when leaked from comments' do
|
||||
it 'returns the WpTheme' do
|
||||
@file = 'comments.html'
|
||||
@expected = WpTheme.new(uri, name: 'debug')
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
describe '::find_from_wooframework' do
|
||||
@@ -96,7 +102,6 @@ describe 'WpTheme::Findable' do
|
||||
@expected = WpTheme.new(uri, name: 'Editorial', version: '1.3.5')
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
describe '::find' do
|
||||
@@ -109,7 +114,6 @@ describe 'WpTheme::Findable' do
|
||||
|
||||
context 'when a method is named s_find_from_s' do
|
||||
it 'does not call it' do
|
||||
|
||||
class WpTheme
|
||||
module Findable
|
||||
extend self
|
||||
@@ -117,7 +121,7 @@ describe 'WpTheme::Findable' do
|
||||
end
|
||||
end
|
||||
|
||||
stub_all_to_nil()
|
||||
stub_all_to_nil
|
||||
|
||||
expect { WpTheme.find(uri) }.to_not raise_error
|
||||
end
|
||||
@@ -125,7 +129,7 @@ describe 'WpTheme::Findable' do
|
||||
|
||||
context 'when the theme is not found' do
|
||||
it 'returns nil' do
|
||||
stub_all_to_nil()
|
||||
stub_all_to_nil
|
||||
|
||||
expect(WpTheme.find(uri)).to be_nil
|
||||
end
|
||||
@@ -133,7 +137,7 @@ describe 'WpTheme::Findable' do
|
||||
|
||||
context 'when the theme is found' do
|
||||
it 'returns it, with the :found_from set' do
|
||||
stub_all_to_nil()
|
||||
stub_all_to_nil
|
||||
stub_request(:get, /.+\/the-oracle\/style.css$/).to_return(status: 200)
|
||||
expected = WpTheme.new(uri, name: 'the-oracle')
|
||||
|
||||
|
||||
@@ -7,10 +7,10 @@ describe WpTheme do
|
||||
it_behaves_like 'WpTheme::Vulnerable'
|
||||
it_behaves_like 'WpItem::Vulnerable' do
|
||||
let(:options) { { name: 'the-oracle' } }
|
||||
let(:vulns_file) { MODELS_FIXTURES + '/wp_theme/vulnerable/themes_vulns.json' }
|
||||
let(:db_file) { MODELS_FIXTURES + '/wp_theme/vulnerable/themes_vulns.json' }
|
||||
let(:expected_refs) { {
|
||||
'id' => [2993],
|
||||
'url' => ['Ref 1,Ref 2'],
|
||||
'url' => ['Ref 1', 'Ref 2'],
|
||||
'cve' => ['2011-001'],
|
||||
'secunia' => ['secunia'],
|
||||
'osvdb' => ['osvdb'],
|
||||
|
||||
@@ -65,6 +65,11 @@ describe 'WpVersion::Findable' do
|
||||
@fixture = '/3.5_minified.html'
|
||||
@expected = '3.5'
|
||||
end
|
||||
|
||||
it 'returns 3.5.1' do
|
||||
@fixture = '/3.5.1_mobile.html'
|
||||
@expected = '3.5.1'
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
@@ -178,7 +183,7 @@ describe 'WpVersion::Findable' do
|
||||
|
||||
context 'when no version found' do
|
||||
it 'returns nil' do
|
||||
stub_all_to_nil()
|
||||
stub_all_to_nil
|
||||
@expected = nil
|
||||
end
|
||||
end
|
||||
@@ -188,8 +193,8 @@ describe 'WpVersion::Findable' do
|
||||
found_from = method[/^find_from_(.*)/, 1].sub('_', ' ')
|
||||
|
||||
context "when found from #{found_from}" do
|
||||
it "returns the correct WpVersion" do
|
||||
stub_all_to_nil()
|
||||
it 'returns the correct WpVersion' do
|
||||
stub_all_to_nil
|
||||
|
||||
allow(WpVersion).to receive(method).and_return(number)
|
||||
|
||||
|
||||
@@ -4,20 +4,6 @@ require 'spec_helper'
|
||||
|
||||
describe WpVersion do
|
||||
it_behaves_like 'WpVersion::Vulnerable'
|
||||
it_behaves_like 'WpItem::Vulnerable' do
|
||||
let(:options) { { number: '3.2' } }
|
||||
let(:vulns_file) { MODELS_FIXTURES + '/wp_version/vulnerable/versions_vulns.json' }
|
||||
let(:expected_refs) { {
|
||||
'id' => [2993],
|
||||
'url' => ['Ref 1,Ref 2'],
|
||||
'cve' => ['2011-001'],
|
||||
'secunia' => ['secunia'],
|
||||
'osvdb' => ['osvdb'],
|
||||
'metasploit' => ['exploit/ex1'],
|
||||
'exploitdb' => ['exploitdb']
|
||||
} }
|
||||
let(:expected_vulns) { Vulnerabilities.new << Vulnerability.new('Here I Am', 'SQLI', expected_refs) }
|
||||
end
|
||||
|
||||
subject(:wp_version) { WpVersion.new(uri, options) }
|
||||
let(:uri) { URI.parse('http://example.com/') }
|
||||
@@ -29,4 +15,12 @@ describe WpVersion do
|
||||
end
|
||||
end
|
||||
|
||||
describe '#all' do
|
||||
let(:versions_file) { File.join(MODELS_FIXTURES, 'wp_version', 'findable', 'advanced_fingerprinting', 'wp_versions.xml') }
|
||||
|
||||
it 'returns the array containign the two versions' do
|
||||
expect(WpVersion.all(versions_file)).to eq ['3.2.1', '3.2']
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
@@ -121,4 +121,122 @@ describe 'VersionCompare' do
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
describe '::lesser?' do
|
||||
context 'version checked is newer' do
|
||||
after { expect(VersionCompare::lesser?(@version1, @version2)).to be_truthy }
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = '1.0'
|
||||
@version2 = '2.0'
|
||||
end
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = '1.0'
|
||||
@version2 = '1.1'
|
||||
end
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = '1.0a'
|
||||
@version2 = '1.0b'
|
||||
end
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = '1.0'
|
||||
@version2 = '5000000'
|
||||
end
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = '0'
|
||||
@version2 = '1'
|
||||
end
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = '0.4.2b'
|
||||
@version2 = '2.3.3'
|
||||
end
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = '.47'
|
||||
@version2 = '.50.3'
|
||||
end
|
||||
end
|
||||
|
||||
context 'version checked is older' do
|
||||
after { expect(VersionCompare::lesser?(@version1, @version2)).to be_falsey }
|
||||
|
||||
it 'returns false' do
|
||||
@version1 = '1'
|
||||
@version2 = '0'
|
||||
end
|
||||
|
||||
it 'returns false' do
|
||||
@version1 = '1.0'
|
||||
@version2 = '0.5'
|
||||
end
|
||||
|
||||
it 'returns false' do
|
||||
@version1 = '500000'
|
||||
@version2 = '1'
|
||||
end
|
||||
|
||||
it 'returns false' do
|
||||
@version1 = '1.6.3.7.3.4'
|
||||
@version2 = '1.2.4.567.679.8.e'
|
||||
end
|
||||
|
||||
it 'returns false' do
|
||||
@version1 = '.47'
|
||||
@version2 = '.46.3'
|
||||
end
|
||||
end
|
||||
|
||||
context 'version checked is the same' do
|
||||
after { expect(VersionCompare::lesser?(@version1, @version2)).to be_falsey }
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = '1'
|
||||
@version2 = '1'
|
||||
end
|
||||
|
||||
it 'returns true' do
|
||||
@version1 = 'a'
|
||||
@version2 = 'a'
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context 'version number causes Gem::Version new Exception' do
|
||||
after { expect(VersionCompare::lesser?(@version1, @version2)).to be_falsey }
|
||||
|
||||
it 'returns false' do
|
||||
@version1 = 'a'
|
||||
@version2 = 'b'
|
||||
end
|
||||
end
|
||||
|
||||
context 'one version number is not set' do
|
||||
after { expect(VersionCompare::lesser?(@version1, @version2)).to be_falsey }
|
||||
|
||||
it 'returns false (version2 nil)' do
|
||||
@version1 = '1'
|
||||
@version2 = nil
|
||||
end
|
||||
|
||||
it 'returns false (version1 nil)' do
|
||||
@version1 = nil
|
||||
@version2 = '1'
|
||||
end
|
||||
|
||||
it 'returns false (version2 empty)' do
|
||||
@version1 = '1'
|
||||
@version2 = ''
|
||||
end
|
||||
|
||||
it 'returns false (version1 empty)' do
|
||||
@version1 = ''
|
||||
@version2 = '1'
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -17,7 +17,7 @@ describe 'WebSite' do
|
||||
)
|
||||
end
|
||||
|
||||
describe "#new" do
|
||||
describe '#new' do
|
||||
its(:url) { is_expected.to be === 'http://example.localhost/' }
|
||||
end
|
||||
|
||||
@@ -68,14 +68,14 @@ describe 'WebSite' do
|
||||
|
||||
describe '#xml_rpc_url' do
|
||||
it 'returns the xmlrpc url' do
|
||||
expect(web_site.xml_rpc_url).to be === "http://example.localhost/xmlrpc.php"
|
||||
expect(web_site.xml_rpc_url).to be === 'http://example.localhost/xmlrpc.php'
|
||||
end
|
||||
end
|
||||
|
||||
describe '#has_xml_rpc?' do
|
||||
it 'returns true' do
|
||||
stub_request(:get, web_site.xml_rpc_url).
|
||||
to_return(status: 200, body: "XML-RPC server accepts POST requests only")
|
||||
to_return(status: 200, body: 'XML-RPC server accepts POST requests only')
|
||||
|
||||
expect(web_site).to have_xml_rpc
|
||||
end
|
||||
@@ -116,12 +116,24 @@ describe 'WebSite' do
|
||||
|
||||
expect(web_site.redirection).to eql absolute_location
|
||||
end
|
||||
|
||||
context 'when starts with a ?' do
|
||||
it 'returns the absolute URI' do
|
||||
relative_location = '?p=blog'
|
||||
absolute_location = web_site.uri.merge(relative_location).to_s
|
||||
|
||||
stub_request(:get, web_site.url).to_return(status: 301, headers: { location: relative_location })
|
||||
stub_request(:get, absolute_location)
|
||||
|
||||
expect(web_site.redirection).to eql absolute_location
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context 'when multiple redirections' do
|
||||
it 'returns the last redirection' do
|
||||
first_redirection = 'www.redirection.com'
|
||||
last_redirection = 'redirection.com'
|
||||
first_redirection = 'http://www.redirection.com'
|
||||
last_redirection = 'http://redirection.com'
|
||||
|
||||
stub_request(:get, web_site.url).to_return(status: 301, headers: { location: first_redirection })
|
||||
stub_request(:get, first_redirection).to_return(status: 302, headers: { location: last_redirection })
|
||||
|
||||
@@ -4,6 +4,7 @@ require File.expand_path(File.dirname(__FILE__) + '/wpscan_helper')
|
||||
|
||||
describe WpTarget do
|
||||
subject(:wp_target) { WpTarget.new(target_url, options) }
|
||||
subject(:wp_target_custom) { WpTarget.new(target_url, options_custom) }
|
||||
let(:target_url) { 'http://example.localhost/' }
|
||||
let(:fixtures_dir) { SPEC_FIXTURES_WPSCAN_WP_TARGET_DIR }
|
||||
let(:login_url) { wp_target.uri.merge('wp-login.php').to_s }
|
||||
@@ -15,10 +16,17 @@ describe WpTarget do
|
||||
wp_plugins_dir: 'wp-content/plugins'
|
||||
}
|
||||
}
|
||||
let(:options_custom) {
|
||||
{
|
||||
config_file: SPEC_FIXTURES_CONF_DIR + '/browser.conf.json',
|
||||
cache_ttl: 0,
|
||||
wp_content_dir: 'custom-content',
|
||||
wp_plugins_dir: 'custom-content/plugins'
|
||||
}
|
||||
}
|
||||
|
||||
before { Browser::reset }
|
||||
|
||||
it_behaves_like 'WpTarget::Malwares'
|
||||
it_behaves_like 'WpTarget::WpReadme'
|
||||
it_behaves_like 'WpTarget::WpRegistrable'
|
||||
it_behaves_like 'WpTarget::WpConfigBackup'
|
||||
@@ -70,6 +78,11 @@ describe WpTarget do
|
||||
expect(wp_target).to be_wordpress
|
||||
end
|
||||
|
||||
it 'returns true if a custom content directory is detected' do
|
||||
stub_request_to_fixture(url: wp_target_custom.url, fixture: fixtures_dir + '/wp_content_dir/wordpress-3.4.1-custom.htm')
|
||||
expect(wp_target_custom).to be_wordpress
|
||||
end
|
||||
|
||||
it 'returns true if the xmlrpc is found' do
|
||||
stub_request(:get, wp_target.xml_rpc_url).
|
||||
to_return(status: 200, body: File.new(fixtures_dir + '/xmlrpc.php'))
|
||||
@@ -136,7 +149,7 @@ describe WpTarget do
|
||||
|
||||
after :each do
|
||||
allow(wp_target).to receive_messages(wp_content_dir: 'wp-content')
|
||||
stub_request_to_fixture(url: wp_target.debug_log_url(), fixture: @fixture)
|
||||
stub_request_to_fixture(url: wp_target.debug_log_url, fixture: @fixture)
|
||||
expect(wp_target.has_debug_log?).to be === @expected
|
||||
end
|
||||
|
||||
|
||||
@@ -32,6 +32,11 @@ describe 'WpscanOptions' do
|
||||
@wpscan_options.url = url
|
||||
expect(@wpscan_options.url).to be === url
|
||||
end
|
||||
|
||||
it 'should encode IDN' do
|
||||
@wpscan_options.url = 'http://пример.испытание/'
|
||||
expect(@wpscan_options.url).to be === 'http://xn--e1afmkfd.xn--80akhbyknj4f/'
|
||||
end
|
||||
end
|
||||
|
||||
describe '#threads=' do
|
||||
|
||||
@@ -1,47 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
require File.expand_path(File.dirname(__FILE__) + '/../../wpstools_helper')
|
||||
|
||||
describe 'StatsPlugin' do
|
||||
subject(:stats) { StatsPlugin.new }
|
||||
let(:plugins_vulns) { MODELS_FIXTURES + '/wp_plugin/vulnerable/plugins_vulns.json' }
|
||||
let(:themes_vulns) { MODELS_FIXTURES + '/wp_theme/vulnerable/themes_vulns.json' }
|
||||
let(:plugins_file) { COLLECTIONS_FIXTURES + '/wp_plugins/detectable/targets.txt' }
|
||||
let(:themes_file) { COLLECTIONS_FIXTURES + '/wp_themes/detectable/targets.txt'}
|
||||
|
||||
describe '#vuln_plugin_count' do
|
||||
it 'returns the correct number' do
|
||||
expect(stats.vuln_plugin_count(plugins_vulns)).to eq 2
|
||||
end
|
||||
end
|
||||
|
||||
describe '#vuln_theme_count' do
|
||||
it 'returns the correct number' do
|
||||
expect(stats.vuln_theme_count(themes_vulns)).to eq 2
|
||||
end
|
||||
end
|
||||
|
||||
describe '#plugin_vulns_count' do
|
||||
it 'returns the correct number' do
|
||||
expect(stats.plugin_vulns_count(plugins_vulns)).to eq 3
|
||||
end
|
||||
end
|
||||
|
||||
describe '#theme_vulns_count' do
|
||||
it 'returns the correct number' do
|
||||
expect(stats.theme_vulns_count(themes_vulns)).to eq 3
|
||||
end
|
||||
end
|
||||
|
||||
describe '#total_plugins' do
|
||||
it 'returns the correct numer' do
|
||||
expect(stats.total_plugins(plugins_file)).to eq 3
|
||||
end
|
||||
end
|
||||
|
||||
describe '#total_themes' do
|
||||
it 'returns the correct numer' do
|
||||
expect(stats.total_themes(themes_file)).to eq 3
|
||||
end
|
||||
end
|
||||
end
|
||||
@@ -1,4 +0,0 @@
|
||||
# encoding: UTF-8
|
||||
|
||||
require 'spec_helper'
|
||||
require WPSTOOLS_LIB_DIR + '/wpstools_helper'
|
||||
@@ -1,58 +1,64 @@
|
||||
[
|
||||
{
|
||||
"mr-smith":{
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2989,
|
||||
"title":"Administrator-exploitable blind SQLi in WordPress 1.0 - 3.8.1",
|
||||
"references":"https://security.dxw.com/advisories/sqli-in-wordpress-3-6-1/,http://www.example.com",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:43:41.000Z"
|
||||
{
|
||||
"mr-smith": {
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2989,
|
||||
"title":"Administrator-exploitable blind SQLi in WordPress 1.0 - 3.8.1",
|
||||
"references": {
|
||||
"url": "https://security.dxw.com/advisories/sqli-in-wordpress-3-6-1/,http://www.example.com"
|
||||
},
|
||||
{
|
||||
"id":2990,
|
||||
"title":"Potential Authentication Cookie Forgery",
|
||||
"references":"https://labs.mwrinfosecurity.com/blog/2014/04/11/wordpress-auth-cookie-forgery/,https://github.com/WordPress/WordPress/commit/78a915e0e5927cf413aa6c2cef2fca3dc587f8be",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:43:41.000Z"
|
||||
},
|
||||
{
|
||||
"id":2990,
|
||||
"title":"Potential Authentication Cookie Forgery",
|
||||
"references": {
|
||||
"url": "https://labs.mwrinfosecurity.com/blog/2014/04/11/wordpress-auth-cookie-forgery/,https://github.com/WordPress/WordPress/commit/78a915e0e5927cf413aa6c2cef2fca3dc587f8be",
|
||||
"osvdb":"105620",
|
||||
"cve":"2014-0166",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
"cve":"2014-0166"
|
||||
},
|
||||
{
|
||||
"id":2991,
|
||||
"title":"Privilege escalation: contributors publishing posts",
|
||||
"references":"https://github.com/wpscanteam/wpscan/wiki/CVE-2014-0165",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
},
|
||||
{
|
||||
"id":2991,
|
||||
"title":"Privilege escalation: contributors publishing posts",
|
||||
"references": {
|
||||
"url": "https://github.com/wpscanteam/wpscan/wiki/CVE-2014-0165",
|
||||
"osvdb":"105630",
|
||||
"cve":"2014-0165",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
"cve":"2014-0165"
|
||||
},
|
||||
{
|
||||
"id":2992,
|
||||
"title":"Plupload Unspecified XSS",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
},
|
||||
{
|
||||
"id":2992,
|
||||
"title":"Plupload Unspecified XSS",
|
||||
"references": {
|
||||
"osvdb":"105622",
|
||||
"secunia":"57769",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
}
|
||||
]
|
||||
}
|
||||
"secunia":"57769"
|
||||
},
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"neo":{
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2993,
|
||||
"title":"wp-admin/options-writing.php Cleartext Admin Credentials Disclosure",
|
||||
"references":"http://seclists.org/fulldisclosure/2013/Dec/135",
|
||||
"osvdb":"101101",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z"
|
||||
}
|
||||
]
|
||||
}
|
||||
"neo": {
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2993,
|
||||
"title":"wp-admin/options-writing.php Cleartext Admin Credentials Disclosure",
|
||||
"references": {
|
||||
"url": "http://seclists.org/fulldisclosure/2013/Dec/135",
|
||||
"osvdb":"101101"
|
||||
},
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z"
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@@ -1,58 +1,64 @@
|
||||
[
|
||||
{
|
||||
"mr-smith":{
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2989,
|
||||
"title":"Administrator-exploitable blind SQLi in WordPress 1.0 - 3.8.1",
|
||||
"references":"https://security.dxw.com/advisories/sqli-in-wordpress-3-6-1/,http://www.example.com",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:43:41.000Z"
|
||||
{
|
||||
"mr-smith": {
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2989,
|
||||
"title":"Administrator-exploitable blind SQLi in WordPress 1.0 - 3.8.1",
|
||||
"references": {
|
||||
"url": "https://security.dxw.com/advisories/sqli-in-wordpress-3-6-1/,http://www.example.com"
|
||||
},
|
||||
{
|
||||
"id":2990,
|
||||
"title":"Potential Authentication Cookie Forgery",
|
||||
"references":"https://labs.mwrinfosecurity.com/blog/2014/04/11/wordpress-auth-cookie-forgery/,https://github.com/WordPress/WordPress/commit/78a915e0e5927cf413aa6c2cef2fca3dc587f8be",
|
||||
"osvdb":"105620",
|
||||
"cve":"2014-0166",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:43:41.000Z"
|
||||
},
|
||||
{
|
||||
"id":2990,
|
||||
"title":"Potential Authentication Cookie Forgery",
|
||||
"references": {
|
||||
"url": "https://labs.mwrinfosecurity.com/blog/2014/04/11/wordpress-auth-cookie-forgery/,https://github.com/WordPress/WordPress/commit/78a915e0e5927cf413aa6c2cef2fca3dc587f8be"
|
||||
},
|
||||
{
|
||||
"id":2991,
|
||||
"title":"Privilege escalation: contributors publishing posts",
|
||||
"references":"https://github.com/wpscanteam/wpscan/wiki/CVE-2014-0165",
|
||||
"osvdb":"105620",
|
||||
"cve":"2014-0166",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
},
|
||||
{
|
||||
"id":2991,
|
||||
"title":"Privilege escalation: contributors publishing posts",
|
||||
"references": {
|
||||
"url": "https://github.com/wpscanteam/wpscan/wiki/CVE-2014-0165",
|
||||
"osvdb":"105630",
|
||||
"cve":"2014-0165",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
"cve":"2014-0165"
|
||||
},
|
||||
{
|
||||
"id":2992,
|
||||
"title":"Plupload Unspecified XSS",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
},
|
||||
{
|
||||
"id":2992,
|
||||
"title":"Plupload Unspecified XSS",
|
||||
"references": {
|
||||
"osvdb":"105622",
|
||||
"secunia":"57769",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
}
|
||||
]
|
||||
}
|
||||
"secunia":"57769"
|
||||
},
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"neo":{
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2993,
|
||||
"title":"wp-admin/options-writing.php Cleartext Admin Credentials Disclosure",
|
||||
"references":"http://seclists.org/fulldisclosure/2013/Dec/135",
|
||||
"osvdb":"101101",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z"
|
||||
}
|
||||
]
|
||||
}
|
||||
"neo": {
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2993,
|
||||
"title":"wp-admin/options-writing.php Cleartext Admin Credentials Disclosure",
|
||||
"references": {
|
||||
"url": "http://seclists.org/fulldisclosure/2013/Dec/135",
|
||||
"osvdb":"101101"
|
||||
},
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z"
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@@ -1,58 +1,65 @@
|
||||
[
|
||||
{
|
||||
"shopperpress":{
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2989,
|
||||
"title":"Administrator-exploitable blind SQLi in WordPress 1.0 - 3.8.1",
|
||||
"references":"https://security.dxw.com/advisories/sqli-in-wordpress-3-6-1/,http://www.example.com",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:43:41.000Z"
|
||||
{
|
||||
"shopperpress": {
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2989,
|
||||
"title":"Administrator-exploitable blind SQLi in WordPress 1.0 - 3.8.1",
|
||||
"references": {
|
||||
"url": "https://security.dxw.com/advisories/sqli-in-wordpress-3-6-1/,http://www.example.com"
|
||||
},
|
||||
{
|
||||
"id":2990,
|
||||
"title":"Potential Authentication Cookie Forgery",
|
||||
"references":"https://labs.mwrinfosecurity.com/blog/2014/04/11/wordpress-auth-cookie-forgery/,https://github.com/WordPress/WordPress/commit/78a915e0e5927cf413aa6c2cef2fca3dc587f8be",
|
||||
"osvdb":"105620",
|
||||
"cve":"2014-0166",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:43:41.000Z"
|
||||
},
|
||||
{
|
||||
"id":2990,
|
||||
"title":"Potential Authentication Cookie Forgery",
|
||||
"references": {
|
||||
"url": "https://labs.mwrinfosecurity.com/blog/2014/04/11/wordpress-auth-cookie-forgery/,https://github.com/WordPress/WordPress/commit/78a915e0e5927cf413aa6c2cef2fca3dc587f8be",
|
||||
"osvdb":"105620",
|
||||
"cve":"2014-0166"
|
||||
},
|
||||
{
|
||||
"id":2991,
|
||||
"title":"Privilege escalation: contributors publishing posts",
|
||||
"references":"https://github.com/wpscanteam/wpscan/wiki/CVE-2014-0165",
|
||||
"osvdb":"105630",
|
||||
"cve":"2014-0165",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
},
|
||||
{
|
||||
"id":2991,
|
||||
"title":"Privilege escalation: contributors publishing posts",
|
||||
"references": {
|
||||
"url": "https://github.com/wpscanteam/wpscan/wiki/CVE-2014-0165",
|
||||
"osvdb":"105630",
|
||||
"cve":"2014-0165"
|
||||
},
|
||||
{
|
||||
"id":2992,
|
||||
"title":"Plupload Unspecified XSS",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
},
|
||||
{
|
||||
"id":2992,
|
||||
"title":"Plupload Unspecified XSS",
|
||||
"references": {
|
||||
"osvdb":"105622",
|
||||
"secunia":"57769",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
}
|
||||
]
|
||||
}
|
||||
"secunia":"57769"
|
||||
},
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z",
|
||||
"fixed_in":"3.8.2"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"webfolio":{
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2993,
|
||||
"title":"wp-admin/options-writing.php Cleartext Admin Credentials Disclosure",
|
||||
"references":"http://seclists.org/fulldisclosure/2013/Dec/135",
|
||||
"osvdb":"101101",
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z"
|
||||
}
|
||||
]
|
||||
}
|
||||
"webfolio": {
|
||||
"vulnerabilities":[
|
||||
{
|
||||
"id":2993,
|
||||
"title":"wp-admin/options-writing.php Cleartext Admin Credentials Disclosure",
|
||||
"references": {
|
||||
"url": "http://seclists.org/fulldisclosure/2013/Dec/135",
|
||||
"osvdb":"101101"
|
||||
},
|
||||
"created_at":"2014-07-28T12:10:07.000Z",
|
||||
"updated_at":"2014-07-28T12:10:07.000Z"
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
|
||||
@@ -1,12 +1,14 @@
|
||||
{
|
||||
"id": "3911",
|
||||
"title": "Vuln Title",
|
||||
"url": "Ref 1,Ref 2",
|
||||
"secunia": "secunia",
|
||||
"osvdb": "osvdb",
|
||||
"cve": "2011-001",
|
||||
"metasploit": "exploit/ex1",
|
||||
"exploitdb": "exploitdb",
|
||||
"references":{
|
||||
"url": "Ref 1,Ref 2",
|
||||
"secunia": "secunia",
|
||||
"osvdb": "osvdb",
|
||||
"cve": "2011-001",
|
||||
"metasploit": "exploit/ex1",
|
||||
"exploitdb": "exploitdb"
|
||||
},
|
||||
"created_at": "2014-07-28T12:10:45.000Z",
|
||||
"updated_at": "2014-07-28T12:10:45.000Z",
|
||||
"type": "CSRF",
|
||||
|
||||
@@ -0,0 +1,103 @@
|
||||
=== A Capture Contact Form (and tab) by AWebVoice.com ===
|
||||
Contributors: AWebVoice
|
||||
Donate link:
|
||||
Tags: contact form, web form, capture contact form, response forms, captcha form, get response, contact me, contact form 7
|
||||
Requires at least: 2.0.2
|
||||
Tested up to: 3.1.1
|
||||
Stable tag: trunk
|
||||
|
||||
Get a contact form and a contact button. Capture your visitors and turn them into customers!
|
||||
|
||||
== Description ==
|
||||
|
||||
A fully customizable contact form on your WordPress blog. And a contact tab to increase customer interaction. Join our fast growing users base who have chosen AWebVoice as their contact form of choice!
|
||||
|
||||
= Get your FREE Contact Form plugin for Wordpress =
|
||||
|
||||
Our Contact Form plugin is full of features that no other wordpress contact form can offer. See for yourself, below are a few of the features we offer:
|
||||
|
||||
* Add a customized contact form to your Wordpress blog which includes a message, contact's email, name, phone number and more!
|
||||
* Create and customize your contact form settings right from within your Wordpress Admin Panel
|
||||
* Include your logo, business contact info, even social links right on your contact form
|
||||
* Notifications: Get a contacts message notifications to your inbox!
|
||||
* Setup multiple autoresponder for your contact form so your visitors get an instant message from you
|
||||
* Take your autoresponders to the next level, and ask your contact to join your email list.
|
||||
* Setup a custom success message or URL for your contact form
|
||||
* Each form has built in ROI tracking
|
||||
* Increases conversion: Include a custom “Contact†tab to the side of your wordpress blog that pops up your contact form.
|
||||
* ...these features will always be free, but go to the next level and get many more features for your contact form!
|
||||
|
||||
= More than a Contact Form =
|
||||
|
||||
Behind the AWebVoice wordpress plugin contact form is a suite of online tools to effectively manage all of your leads, contacts, and marketing ROI needs. As leads come in from your contact form, those contacts are automatically added to your online contacts database. From there, access information about each contact, send emails to each contact, and fully track, organize, and manage your communications. AWebVoice.com is designed to scale from single person offices to Fortune 500 companies -- and it is created on the very largest online database has to offer.
|
||||
|
||||
|
||||
= And it is easy to get start =
|
||||
|
||||
AWebVoice.com’s contact form is FREE and is the easiest wordpress contact form to use. We think you will agree, give it a try sign up now:
|
||||
www.awebvoice.com.
|
||||
|
||||
== Installation ==
|
||||
|
||||
= Option 1: Install the plugin via your Wordpress admin panel =
|
||||
1. Login to your Wordpress system which should take you to the Dashboard of your Wordpress account.
|
||||
1. Click the "Plugins" menu on the left menu bar. The choose "Add New".
|
||||
1. Search for "AWebVoice", "Contact " or "contact form".
|
||||
1. Click Install Now, the "Contact Form" by AWebVoice.com.
|
||||
1. After installation has finished, you need to activate the plugin.
|
||||
1. You should see the AWebVoice plugin listed in the available plugins. Click the "Activate" link.
|
||||
1. Next, click the "Settings" menu on the left menu bar and choose "AWebVoice Form"
|
||||
1. A form will be presented. Enter the e-mail address to receive contact form messages, and click "Create Account".
|
||||
1. Your AWebVoice tab-button and contact form have been installed and are working on your blog.
|
||||
|
||||
= Option 2: Manual plugin installation =
|
||||
1. Click on the red "Download Version x.x" button on the right side of this page.
|
||||
1. After the download has finished, extract the files.
|
||||
1. Upload the "awebvoivce" folder to your server in "/wp-content/plugins" directory
|
||||
1. Login to you Wordpress system which should take you to the admin panel or Dashboard. Click on "Plugins" menu.
|
||||
1. You should see the AWebVoice plugin listed in the available plugins. Click the "Activate" link.
|
||||
1. Then click on the "Settings" menu in the left side menu bar. Choose "AWebVoice Form"
|
||||
1. A form will be presented. Enter the e-mail address to receive contact form messages, and click "Create Account".
|
||||
1. Your AWebVoice tab-button and contact form have been installed and are working on your blog.
|
||||
|
||||
== Frequently Asked Questions ==
|
||||
|
||||
= What is Contact Form by AWebVoice.com? =
|
||||
Unlike other contact form providers like contact form 7, you will never have to touch a line of code to create, edit, or modify your contact form. Just install the Awebvoice.com contact form plugin, choose the email address you want your form submissions to go to, and that is it. Your new contacts are delivered to the specified email address AND stored in an online database under your name. Your contacts are yours and not shared with others. How you use your new contacts is up to you.
|
||||
|
||||
= Can I customize my contact form? =
|
||||
Yes. Editing a form is quick and easy. In your WordPress administration page, click on Settings. Click on the AWebVoice plugin and click the modify button to edit your contact form. (You may have to login first to AWebVoice.com) With the AWebVoice contact form editor, you can create a beautiful and customized contact forms, including your logo, your address and phone, and more.
|
||||
|
||||
= What is the AWebVoice tab-button? =
|
||||
The tab-button is a button that sits on the side of your blog and maintains position even as your visitors scroll. Your potential new contacts or existing contacts are only one click away from sending you a message! When the button is clicked, your contact form pops right up in a nice modal window, darkening the rest of the screen and focusing the user on completing your contact form. This AWebVoice tab-button and contact form combination has been proven improve conversions on a website by over 45%.
|
||||
|
||||
= What other unique features do you offer? =
|
||||
Many more features. AWebVoice is a full featured email, newsletter, coupon marketing system. The tab-button and contact form will always be free. But if you need more, such as self-managed email lists, we have it. We also have ROI reports so you can track your contact form and blog success rate. The AWebVoice Email/Newsletter management system is a subscription based system. We want to help you get started, and once the task of managing your contact list get too large, we are there to support your efforts. AWebVoice is the most effective marketing tool a small or large business can have.
|
||||
|
||||
Get your free AWebVoice contact form today and start watching your leads grow!
|
||||
|
||||
== Screenshots ==
|
||||
|
||||
1. Contact Form Admin Panel
|
||||
2. A Contact Form
|
||||
3. Contact Tab-Button on the Blog (click opens contact form)
|
||||
|
||||
== Change Log ==
|
||||
|
||||
= Coming Soon =
|
||||
* Contact Form: More custom from fields for your contact form
|
||||
* Contact Form: More languages for button and contact form
|
||||
|
||||
= 3.1 =
|
||||
* Initial WordPress Release.
|
||||
* Analytics included in Contact Form
|
||||
* Custom form fields for your contact form
|
||||
* Form title is editable
|
||||
|
||||
== Upgrade Notice ==
|
||||
|
||||
= 1.0 =
|
||||
Upgrade notices when available will be described in this section.
|
||||
|
||||
= Languages =
|
||||
* English: Available contact form and button
|
||||
@@ -0,0 +1,13 @@
|
||||
=== Plugin Name ===
|
||||
AA health calculator
|
||||
|
||||
|
||||
|
||||
Tags:aa ,health,calculator
|
||||
Requires at least:4.0
|
||||
Tested up to:4.0
|
||||
Stable tag:aahealthcalculator
|
||||
License: GPL
|
||||
Contributors :A and A
|
||||
==Description==
|
||||
use [health] shortcode
|
||||
@@ -0,0 +1,215 @@
|
||||
=== Advanced Most Recent Posts Mod ===
|
||||
Contributors: yakuphan, trepmal
|
||||
Tags: Advanced, recent, recent posts, most recent, category posts, thumbnail
|
||||
Donate link: http://kaileylampert.com/donate/
|
||||
Requires at least: 2.8
|
||||
Tested up to: 3.2.1
|
||||
Stable tag: trunk
|
||||
|
||||
Based off the Advanced Most Recent Posts plugin by Yakup GÖVLER. Display most recent posts from selected categories or current category or all categories with thumbnail images (optional).
|
||||
|
||||
== Description ==
|
||||
Advanced Most Recent Posts Widget displays your recent posts with thumbnail images (optional). It gets posts from selected categories or current category or all categories. When your visitors are at home, it gets posts from all posts or selected category. If you set 'Get posts from current category', when visitors see single post, widget lists posts in the same category of single post or when visitors click a category link, it gets posts from current category.
|
||||
|
||||
Check out a brand new plugin inspired by this one: [Mini Loops](http://wordpress.org/extend/plugins/mini-loops/)
|
||||
|
||||
I'm bad at support (not intentionally). If you have questions: check the forums, then check [my blog post's comment thread](http://trepmal.com/plugins/advanced-most-recent-posts-mod/#comments). If that doesn't work, post to the forums (there are awesome volunteers out there!) and get my attention by pinging me on twitter [@trepmal](http://twitter.com/trepmal).
|
||||
|
||||
== Installation ==
|
||||
|
||||
= Installation =
|
||||
1. Make sure you are running WordPress version 2.8 or better. It won't work with older versions.
|
||||
2. Download the zip file and extract the contents.
|
||||
3. Upload the 'advanced-most-recent-posts' folder (wp-content/plugins/).
|
||||
4. Activate the plugin through the 'plugins' page in WP.
|
||||
5. See 'Appearance'->'Widgets' to place it on your sidebar. Set the settings.
|
||||
|
||||
== Frequently Asked Questions ==
|
||||
|
||||
= How can I set it to get posts from current category? =
|
||||
Select checkbox on widget's settings called 'Get posts from current category'.
|
||||
|
||||
= I want to display only the posts in two categories. =
|
||||
You have to write their category's ids -separated with a comma- to 'Categories' textbox.
|
||||
|
||||
= I don't use Widgets. How can use this widget? =
|
||||
|
||||
template tag: `yg_recentposts( $args )`
|
||||
shortcode: `[amrp]` with args
|
||||
Original author's [website](http://www.yakupgovler.com/?p=1033).
|
||||
|
||||
= .... Image alignment .... =
|
||||
|
||||
If you need serious customization, please go learn CSS. I will not provide extensive CSS support. (Sorry - there are just far too many variations, and I do all this in my spare time)
|
||||
|
||||
The most frequest request I get has to do with aligning the image to the right or left. To get started with customization, create a file called amrp-styles.php (really, any name will do) and upload it to `wp-content/mu-plugins` (you may need to create this directory).
|
||||
|
||||
In that file, paste the following
|
||||
`<?php
|
||||
/*
|
||||
AMRP Styles
|
||||
*/
|
||||
|
||||
add_action('wp_head', 'amrp_styles');
|
||||
function amrp_styles() {
|
||||
?>
|
||||
<style type="text/css">
|
||||
.advanced-recent-posts {
|
||||
/* remove bullet points */
|
||||
list-style-type: none;
|
||||
}
|
||||
.advanced-recent-posts li {
|
||||
}
|
||||
.advanced-recent-posts li a {
|
||||
}
|
||||
.advanced-recent-posts li img {
|
||||
float: right; /* change to left if you'd prefer */
|
||||
margin: 3px;
|
||||
}
|
||||
</style>
|
||||
<?php
|
||||
}`
|
||||
|
||||
Of course, if you have the skills, feel free to relocate that CSS.
|
||||
|
||||
== Screenshots ==
|
||||
|
||||
1. Widget's screenshot in 'Appearance'->'Widgets'
|
||||
2. (original version) Widget's screenshot in 'Appearance'->'Widgets'
|
||||
|
||||
== Options ==
|
||||
|
||||
Widget's options allow you to change your recent posts list displaying.
|
||||
|
||||
= Title: =
|
||||
Your recent posts widget's title on your sidebar.
|
||||
|
||||
= Title Link: =
|
||||
The page the title should link to.
|
||||
|
||||
= Hide Post Title: =
|
||||
Check to hide post title in output. useful for thumbnail-only displays
|
||||
|
||||
= Separator: =
|
||||
The character to use to separate the title from the excerpt.
|
||||
|
||||
= After Excerpt: =
|
||||
What should appear after the excerpt
|
||||
|
||||
= After Excerpt Link: =
|
||||
should the 'after excerpt' text link to the post? useful if 'after excerpt' read like "read more..."
|
||||
|
||||
= Show: =
|
||||
The post type to be displayed.
|
||||
|
||||
= Number of posts to show: =
|
||||
How many posts to display
|
||||
|
||||
= Excerpt length (letters) =
|
||||
You know that
|
||||
|
||||
= Thumbnail Custom Field Name =
|
||||
If you want to display the thumbnail of your posts via a custom field, write its name.
|
||||
|
||||
= Height - Width =
|
||||
Images size.
|
||||
|
||||
= Get first image of post =
|
||||
If you don't want to use custom field, plugin will get first image from your post content.
|
||||
|
||||
= Get first attached image of post =
|
||||
Plugin gets first attached image of post.
|
||||
|
||||
= Default image =
|
||||
If post has no image, plugin display this image. Ex: http://www.yakupgovler.com/default-image.png
|
||||
|
||||
|
||||
Notice: If you use three options, plugin uses custom field image firstly. If the post has no custom field, it gets first image from content. At last it gets first attached image. I suggest not to use "Get first image of post" for performance. It queries much more.
|
||||
|
||||
= Show Author =
|
||||
If checked, shows author next to title
|
||||
|
||||
= Show Post Timestamp =
|
||||
If checked, shows post timestamp
|
||||
|
||||
= Time format =
|
||||
The format to be used when displaying the timestamp
|
||||
|
||||
= Put time =
|
||||
A placement option for the post timestamp
|
||||
|
||||
= Categories =
|
||||
Plugin gets posts in these categories. (Category IDs, separated by commas.)
|
||||
|
||||
= Get posts from current category: =
|
||||
Posts will be get from current category (single post's category or current category).
|
||||
|
||||
|
||||
== Upgrade Notice ==
|
||||
|
||||
= 1.6.5 =
|
||||
bugfix: 'after excerpt' now appears as it should even if the link option is unchecked
|
||||
Have you tried [Mini Loops](http://wordpress.org/extend/plugins/mini-loops/)?
|
||||
|
||||
= 1.6.4 =
|
||||
moved image outside of title so it won't disappear if 'hide title' is checked
|
||||
undefined variable bug fix
|
||||
|
||||
= 1.6.3 =
|
||||
fixed after-excerpt-link bug
|
||||
|
||||
= 1.6 =
|
||||
Future updates will assume you have at least this release.
|
||||
|
||||
== Changelog ==
|
||||
|
||||
= 1.6.5.2 =
|
||||
* it title is empty, show nothing not default
|
||||
|
||||
= 1.6.5.1 =
|
||||
* updated POT file
|
||||
|
||||
= 1.6.5 =
|
||||
* bugfix: 'after excerpt' now appears as it should even if the link option is unchecked
|
||||
|
||||
= 1.6.4 =
|
||||
* moved image outside of title so it won't disappear if 'hide title' is checked
|
||||
* undefined variable bug fix
|
||||
|
||||
= 1.6.3 =
|
||||
* fixed after-excerpt-link bug
|
||||
|
||||
= 1.6.2 =
|
||||
* shortcode fixes for 'limit' (really should be 'shownum' - now both work) and height/width
|
||||
|
||||
= 1.6.1 =
|
||||
* author fix
|
||||
|
||||
= 1.6 =
|
||||
* remove 20 post limit
|
||||
* option to display posts in reverse order
|
||||
* excerpt by *word* count option
|
||||
* post-offset option
|
||||
|
||||
= 1.5 =
|
||||
* *dev release*
|
||||
* option to hide post title
|
||||
* option to specify the '...' after excerpt
|
||||
|
||||
= 1.4.1 =
|
||||
* fixed double echo issue
|
||||
|
||||
= 1.4 =
|
||||
* added support for shortcodes, show author option and post-type choice
|
||||
|
||||
= 1.3 =
|
||||
* fixed timestamp bug, added timestamp placement option
|
||||
|
||||
= 1.2 =
|
||||
* added support for setting a title link, choosing a title/content separator, and displaying post timestamp
|
||||
|
||||
= 1.1 =
|
||||
* (original plugin) Fixed a bug. If you don't set image dimensions, it displays thumbnail wrong.
|
||||
|
||||
= Version 1.0 =
|
||||
* Initial release version.
|
||||
@@ -0,0 +1,39 @@
|
||||
=== All In One Facebook ===
|
||||
Contributors: rahadgp
|
||||
Donate link:
|
||||
Tags: facebook,Social Networking,Wordpress Facebook widget, twiter widget
|
||||
Requires at least: 3.3
|
||||
Tested up to: 3.8
|
||||
Stable tag: all in one facebook
|
||||
License: GPLv2 or later
|
||||
License URI: http://www.gnu.org/licenses/gpl-2.0.html
|
||||
|
||||
With this widget and plugin combination , you can display a customizable JQUERY accordion which gathers Facebook social plugins together with option which to be display or which you don't want to display in your side bar or widget area, and by the plugin you can set short code for each and every thing what you want to put in your post on your website .
|
||||
|
||||
== Description ==
|
||||
With this widget , you can display a customizable frame which gathers Facebook social plugins together with option which to be display or which you don't want to display in your side bar or widget area, and by the plugin you can set short code for each and every thing what you want to put in your post on your website . As a whole new feature like and share feature has been implemented with like box, recommends and twitter feed integration.
|
||||
|
||||
== Installation ==
|
||||
|
||||
1. Upload `plugin-name.php` to the `/wp-content/plugins/` directory
|
||||
1. Activate the plugin through the 'Plugins' menu in WordPress
|
||||
|
||||
== Frequently asked questions ==
|
||||
|
||||
|
||||
|
||||
== Screenshots ==
|
||||
1. Setting Page for the facebook plugin
|
||||
2. Setting page
|
||||
3. Setting Page
|
||||
|
||||
|
||||
== Changelog ==
|
||||
|
||||
|
||||
|
||||
== Upgrade notice ==
|
||||
|
||||
|
||||
|
||||
== Arbitrary section 1 ==
|
||||
@@ -0,0 +1,224 @@
|
||||
=== Backup Scheduler ===
|
||||
|
||||
Author: SedLex
|
||||
Contributors: SedLex
|
||||
Author URI: http://www.sedlex.fr/
|
||||
Plugin URI: http://wordpress.org/plugins/backup-scheduler/
|
||||
Tags: backup, schedule, plugin, save, database, zip
|
||||
Requires at least: 3.0
|
||||
Tested up to: 4.2
|
||||
Stable tag: trunk
|
||||
License: GPLv3
|
||||
|
||||
With this plugin, you may plan the backup of your entire website (folders, files and/or database).
|
||||
|
||||
== Description ==
|
||||
|
||||
With this plugin, you may plan the backup of your entire website (folders, files and/or database).
|
||||
|
||||
You can choose:
|
||||
|
||||
* which folders you want to save;
|
||||
* the frequency of the backup process;
|
||||
* whether your database should be saved;
|
||||
* whether the backup is stored on the local website, sent by email or stored on a distant FTP (support of multipart zip files)
|
||||
|
||||
This plugin is under GPL licence
|
||||
|
||||
= Multisite - Wordpress MU =
|
||||
|
||||
This plugin is compatible with Multisite installation.
|
||||
|
||||
Each blog administrator may save their own data.
|
||||
|
||||
The super-admin may save either its data or the whole website. By saving the whole site, the admin may create different SQL files for the subsite in order to ease the restoration of a single sub-site.
|
||||
|
||||
= Localization =
|
||||
|
||||
* German (Switzerland) translation provided by PeterDbbert, BernhardKnab, scream
|
||||
* German (Germany) translation provided by agent-test, agent, bartdev2000, Ditoran, GLassnig
|
||||
* English (United States), default language
|
||||
* Spanish (Spain) translation provided by Javier, AVfoto, charliechin, IgnacioCalvo, JordiVives, FelipeJAG
|
||||
* Farsi (Iran) translation provided by sehrama.ir
|
||||
* Finnish (Finland) translation provided by AnttiSilvola
|
||||
* French (France) translation provided by SedLex, wkpixearts, Matthieu, mutmut, anonymous, noaneo, TonyLand
|
||||
* Indonesian (Indonesia) translation provided by ceceparif
|
||||
* Indonesian (Indonesia) translation provided by Faleddo
|
||||
* Italian (Italy) translation provided by PuntoCon
|
||||
* Dutch (Netherlands) translation provided by Matrix, WybAnema, Jay
|
||||
* Polish (Poland) translation provided by Opti, Lukasz, pablo, Misiek, MarekMackiewicz, Darbo
|
||||
* Portuguese (Brazil) translation provided by RainilsonRodriguis, GuiBeloto
|
||||
* Portuguese (Portugal) translation provided by FranciscoRocha
|
||||
* Russian (Russia) translation provided by GerinG, Slawka, Berdych
|
||||
* Swedish (Sweden) translation provided by
|
||||
* Thai (Thailand) translation provided by tontan
|
||||
* Turkish (Turkey) translation provided by UfukArt
|
||||
* Chinese (People's Republic of China) translation provided by YiscaJoe, jeffli
|
||||
|
||||
= Features of the framework =
|
||||
|
||||
This plugin uses the SL framework. This framework eases the creation of new plugins by providing tools and frames (see dev-toolbox plugin for more info).
|
||||
|
||||
You may easily translate the text of the plugin and submit it to the developer, send a feedback, or choose the location of the plugin in the admin panel.
|
||||
|
||||
Have fun !
|
||||
|
||||
== Installation ==
|
||||
|
||||
1. Upload this folder backup-scheduler to your plugin directory (for instance '/wp-content/plugins/')
|
||||
2. Activate the plugin through the 'Plugins' menu in WordPress
|
||||
3. Navigate to the 'SL plugins' box
|
||||
4. All plugins developed with the SL core will be listed in this box
|
||||
5. Enjoy !
|
||||
|
||||
== Screenshots ==
|
||||
|
||||
1. A list of all backup files
|
||||
2. The configuration page of the plugin
|
||||
|
||||
== Changelog ==
|
||||
|
||||
= 1.5.9 =
|
||||
* NEW: Add icons
|
||||
|
||||
= 1.5.8 =
|
||||
* NEW: Exclusion folder is now possible with regexp
|
||||
|
||||
= 1.5.7 =
|
||||
* NEW: Exclusion folder enabled
|
||||
* NEW: Detailed HOW TO
|
||||
|
||||
= 1.5.6 =
|
||||
* BUG : Problem of activation with version of PHP below 5.2
|
||||
|
||||
= 1.5.5 =
|
||||
* NEW : Take into account blogs.dir and site
|
||||
|
||||
= 1.5.4 =
|
||||
* NEW : By saving the whole site, the admin may create different SQL files for the subsite in order to ease the restoration of a single sub-site.
|
||||
|
||||
= 1.5.3 =
|
||||
* BUG: On some configuration, <? is not supported
|
||||
|
||||
= 1.5.2 =
|
||||
* NEW: You may now create subfolder in the FTP directory
|
||||
* NEW: improve the look of the configuration page
|
||||
|
||||
= 1.5.1 =
|
||||
* BUG: improve the summary mail
|
||||
* NEW: indicate if the FTP transfer has been successful in the backend
|
||||
* NEW: few enhancement in the framework
|
||||
|
||||
= 1.5.0 =
|
||||
* Major improvement of the database backup
|
||||
* the summary mail now displays the issues with the ftp transfer
|
||||
|
||||
= 1.4.0 -> 1.4.4 =
|
||||
* Change the URL of the plugin on Wordpress
|
||||
* Some modification
|
||||
* Some issues in the framework
|
||||
* Cleaning the framework to avoid unnecessarly code
|
||||
* A bug that do not delete the lock file when reseting the backup process
|
||||
* Enhance the performance of the backup process and ensure error protection
|
||||
* Improve the mail summary
|
||||
* Enhance the feedback tab
|
||||
* Improve the core
|
||||
|
||||
= 1.3.0 -> 1.3.7 =
|
||||
* FTP bug with some webhosting service
|
||||
* FTP port may be changed
|
||||
* The error message is muck more explicit
|
||||
* Add a drop if exist in SQL table
|
||||
* Bug with multisite and remove a false positive error with wordfence
|
||||
* There was a bug in the regexp when the ftp were directed to the root folder without any slash at the end.
|
||||
* Add deletion features when uninstalling the plugin
|
||||
* Multisite compatible
|
||||
* Improve the zip compatibilities
|
||||
* Add log features
|
||||
|
||||
= 1.2.0 -> 1.2.8 =
|
||||
* Some spanned zip files were corrupted due to a bug in the index
|
||||
* Remove short_open_tag
|
||||
* Tuning to be able to work with very huge database
|
||||
* Bug with NULL values in the database
|
||||
* FTP support
|
||||
* Full site backup is now possible
|
||||
* Bug correction when SQL has NULL value
|
||||
* Add a link to delete manually the backup (feature requested by Mirza)
|
||||
* You can also force a new update without sending the emails
|
||||
* Improve error management and memory leakage
|
||||
|
||||
= 1.1.0 -> 1.1.5 =
|
||||
* Bug in the sql file : date and time managements were incorrect
|
||||
* Add a time option for choosing the best moment to perform an automatic backup
|
||||
* Display bug correction
|
||||
* Add instructions to restore the backup :)
|
||||
* Improve memory and time management for database extraction
|
||||
* Add error messages if it is impossible to read/delete/modify files
|
||||
* Add time and memory management for constrained configuration
|
||||
* Improving zip decompression and path
|
||||
* Correction of a bug that occurs when server refuse to access / directory "open_basedir" restriction
|
||||
* Update of the core
|
||||
|
||||
= 1.0.1 =
|
||||
* First release in the wild web (enjoy)
|
||||
|
||||
== Frequently Asked Questions ==
|
||||
|
||||
= Forced backup never ends (but there is no displayed error) =
|
||||
|
||||
Be sure to stay on the configuration page : if you quit the page, the forced backup process will be killed !
|
||||
|
||||
= Scheduled backup is stucked =
|
||||
|
||||
Scheduled backup only works on website that have traffic.
|
||||
|
||||
Indeed, each visits triggers a piece of the backup process.
|
||||
|
||||
Thus, if there is no traffic, the schedule backup process wont't occur. If there is very little traffic, the backup will be very long, etc
|
||||
|
||||
= I have an error message indicating that another backup is running =
|
||||
|
||||
This message may happen if the chunk size is set quite high. For instance, 40 Mo is clearly too big and server server configuration of many webhosters will kill scripts which use too much memory.
|
||||
|
||||
Most of the case 5Mo is ok.
|
||||
|
||||
If you get this error, set the chunk size to 1Mo and if it solves your problem, increase this chunk size.
|
||||
|
||||
= Compatible Archive Software =
|
||||
|
||||
The backup will be in a multi-part format. In order to uncompress it, you should put all the backup in the same folder and open the .zip file with Winzip.
|
||||
|
||||
You may experience some "corruption" error. It is mainly due that archive software are not compatible with multi-part archives. I have tried with success:
|
||||
|
||||
* Winzip (version 16.0 tested),
|
||||
* WinRar (some issue with UTF8 characters), and
|
||||
* IZArc (some issue with UTF8 characters).
|
||||
|
||||
= NOT-Compatible Archive Software =
|
||||
|
||||
These software are *not* compatible with multi-part archives:
|
||||
|
||||
* 7-zip, and
|
||||
* the Windows Explorer embedded function.
|
||||
|
||||
Do not hesitate to contact me if you face some issues.
|
||||
|
||||
= To restore the backups =
|
||||
|
||||
* install a fresh version of Wordpress on your server ;
|
||||
* unzip the backup (actually, the zip file comprises a plurality of files i.e. a multi-part zip (zip, z01, z02, etc.). These files should be saved in a same folder and your zip program (such as IZArc, Winzip, Winrar, ...) will do the job for you...
|
||||
* If you have configured to save the entire installation, replace all the wordpress files by the one in the zip file and import the SQL files (at the root of the zip file, the files named *.sql1, *sql2, etc.) in your database (with for instance phpmyadmin). It is recommended to save your database first ;
|
||||
* In other cases, replace the 'plugins', 'themes', 'uploads' folders (in the wp-content folder) with the one in the archive, replace the wp-config.php (at the root of your wordpress repository) with the one at the root of the zip file and import the SQL files (at the root of the zip file, the files named *.sql1, *sql2, etc.) in your database (with for instance phpmyadmin). It is recommended to save your database first.
|
||||
|
||||
= The backup files are corrupted =
|
||||
|
||||
Be sure that all thz zip files (i.e. .zip, .z01, z02, etc.) are in the same folder.
|
||||
If you have still this issue, please try with Winzip software.
|
||||
|
||||
* Where can I read more?
|
||||
|
||||
Visit http://www.sedlex.fr/cote_geek/
|
||||
|
||||
|
||||
InfoVersion:f450b43eebb7570fb1ec0ce188b82e8eebae57cd
|
||||
8
spec/samples/common/models/wp_item/versionable/beta1.txt
Normal file
8
spec/samples/common/models/wp_item/versionable/beta1.txt
Normal file
@@ -0,0 +1,8 @@
|
||||
Contributors: Ramoonus
|
||||
Donate link: http://www.ramoonus.nl
|
||||
Tags: Glow, javascript, bbc,
|
||||
Requires at least: 3.9
|
||||
Tested up to: 4.1
|
||||
Stable tag: 2.0.0-beta1
|
||||
|
||||
This plugin adds BBCs Glow Javascript library to your set-up.
|
||||
@@ -0,0 +1,22 @@
|
||||
=== Blog Reordering ===
|
||||
Contributors: The HungryCoder
|
||||
Donate link: http://hungrycoder.xenexbd.com/payme
|
||||
Tags: blog, ordering, reordering, arrangment, sorting
|
||||
Requires at least: 2.6.2
|
||||
Tested up to: 2.6.5
|
||||
Stable Tag:
|
||||
|
||||
Rearrange you blog ordering.
|
||||
|
||||
== Description ==
|
||||
|
||||
Reorder your blog posts in multiple ways including custom ordering instead of typical datewise post display. You can also mark any post as sticky that will be always placed at top.
|
||||
|
||||
== Installation ==
|
||||
This plugin is yet to finalize. Please do not install in live sites.
|
||||
|
||||
1. Upload archive to the `/wp-content/plugins/` directory and unzip.
|
||||
2. Activate the plugin through the 'Plugins' menu in WordPress
|
||||
3. Make your ordering settings from Settings -> Blog Reordering
|
||||
|
||||
I am new to SVN. pardon my mistakes.
|
||||
@@ -0,0 +1,70 @@
|
||||
=== Like This ===
|
||||
Contributors: RosemarieP
|
||||
Tags: karma, likes, post
|
||||
Requires at least: 3.0
|
||||
Tested up to: 3.1
|
||||
Stable tag: trunk
|
||||
|
||||
A simple 'I like this' plugin inspired by the facebook 'like' functionality.
|
||||
|
||||
== Description ==
|
||||
A simple 'I like this' plugin inspired by the facebook 'like' functionality. For visitors who don't want to bother with commenting.
|
||||
http://lifeasrose.ca/2011/03/wordpress-plugin-i-like-this
|
||||
has a blog entry all about it :)
|
||||
|
||||
A big thanks to Dong (ddliuhb@gmail.com) for finding a syntactical error that was causing problems for some people. And thanks to Raphael (ressoosnowdon@googlemail.com) for noticing this error and working hard to figure out what it was.
|
||||
|
||||
== Installation ==
|
||||
|
||||
1. Upload the files into a folder named `roses-like-this` to the `/wp-content/plugins/` directory
|
||||
2. Activate the plugin through the 'Plugins' menu in WordPress
|
||||
3. Place `<?php printLikes(get_the_ID()); ?>` in 'the loop' of your posts wherever you want the 'like this' link to appear.
|
||||
|
||||
|
||||
IMPORTANT!!!!
|
||||
PLEASE MAKE SURE THAT YOUR THEME HAS THE FOLLOWING LINE IN ITS HEADER FILE:
|
||||
`<?php wp_print_scripts(); ?>`
|
||||
|
||||
...Most high quality themes should have this already but if you're writing your own theme or using a custom theme that doesn't include this line, please make sure you include it in header.php, somewhere between `<head>` and `</head>`
|
||||
|
||||
== Frequently Asked Questions ==
|
||||
|
||||
= How can I make the 'like this' link look prettier? =
|
||||
|
||||
With CSS :) Here is the code that I use:
|
||||
`a.done {
|
||||
background:url("http://yoururl.com/wordpress/plugins/roses-like-this/action_check.png") bottom right no-repeat;
|
||||
padding-right:18px;
|
||||
color:#8bcb46;
|
||||
}`
|
||||
|
||||
= The javascript is not working! =
|
||||
|
||||
IMPORTANT!!!!
|
||||
PLEASE MAKE SURE THAT YOUR THEME HAS THE FOLLOWING LINE IN ITS HEADER FILE:
|
||||
`<?php wp_print_scripts(); ?>`
|
||||
|
||||
= The javascript is STILL not working!!! =
|
||||
Do you call get_header() in your theme? This is also needed, although almost certainly there anyway.
|
||||
|
||||
= The javascript is STILL not working AGAIN!!! =
|
||||
The plugin expects to find the javascript file in a folder called `roses-like-this` under /plugins. So if you have named the folder something else, you're probably getting a 404 error!
|
||||
|
||||
To fix, you can either rename your folder `roses-like-this` OR you can edit the `likethis.php` file and edit line `112` roses-like-this/ to yourfoldername/
|
||||
|
||||
== Changelog ==
|
||||
|
||||
= 1.0 =
|
||||
* The very first version of this plugin :)
|
||||
|
||||
= 1.01 =
|
||||
* Made a small change for those of you installing directly from wordpress.org. This changes the default directory from `likeThis` to `roses-like-this` in order to coincide with what wordpress will install. Should lead to less confusion!
|
||||
|
||||
= 1.1 =
|
||||
* Major bug fix! :) Anyone having an issue where the likeThis link clicking wasn't saving in the database should find it fixed.
|
||||
|
||||
= 1.2 =
|
||||
* Bug Fix for those having issues with cookies not being saved correctly.
|
||||
|
||||
= 1.3 =
|
||||
* Added sidebar widget for displaying most liked posts
|
||||
994
spec/samples/common/models/wp_item/versionable/my_calendar.txt
Normal file
994
spec/samples/common/models/wp_item/versionable/my_calendar.txt
Normal file
@@ -0,0 +1,994 @@
|
||||
=== My Calendar ===
|
||||
Contributors: joedolson
|
||||
Donate link: http://www.joedolson.com/donate.php
|
||||
Tags: calendar, dates, times, events, scheduling, event manager, event calendar
|
||||
Requires at least: 3.0.6
|
||||
Tested up to: 3.5.0
|
||||
License: GPLv2 or later
|
||||
Stable tag: trunk
|
||||
|
||||
Accessible WordPress event calendar plugin. Show events from multiple calendars on pages, in posts, or in widgets.
|
||||
|
||||
== Description ==
|
||||
|
||||
My Calendar provides event management and numerous methods to display your events. The plug-in can support individual site calendars within WordPress Multi-User, or multiple calendars displayed by categories of or locations for events.
|
||||
|
||||
* [User's Guide available for purchase](http://www.joedolson.com/articles/my-calendar/users-guide/) with extensive assistance in set up and use.
|
||||
* [Paid plug-in to add front-end event contributions](https://www.joedolson.com/articles/my-calendar/submissions/)
|
||||
|
||||
=Basic Features:=
|
||||
|
||||
* Standard calendar grid or list views of events
|
||||
* Show events in monthly, weekly, or daily view.
|
||||
* Mini-calendar view for compact displays (as widget or as shortcode)
|
||||
* Widget to show today's events
|
||||
* Widget to show upcoming or past events
|
||||
* Custom templates for event output
|
||||
* Limit by category/categories
|
||||
* Limit by location
|
||||
* Limit by author
|
||||
* Disable default CSS and default JavaScript or display only on specific Pages/Posts
|
||||
* Editable CSS styles and JavaScript behaviors
|
||||
* Schedule a wide variety of recurring events.
|
||||
* Individual occurrences of recurring events can be edited individually
|
||||
* Access to most aspects of My Calendar can be restricted by role. (Adding events, editing events, editing styles, changing settings, etc.)
|
||||
* Choose which of the following fields you want to enter and display for each event:
|
||||
* title,
|
||||
* description,
|
||||
* event image,
|
||||
* alternate description,
|
||||
* event host,
|
||||
* event category,
|
||||
* URL,
|
||||
* registration status (open, closed or irrelevant),
|
||||
* event location
|
||||
* Email notification to administrator when events are scheduled or reserved
|
||||
* Location Manager for storing frequently used venues
|
||||
* Fetch events from a remote MySQL database. (Sharing events in a network of sites.)
|
||||
* Import from [Kieran O'Shea's Calendar plugin](http://wordpress.org/extend/plugins/calendar/)
|
||||
* Integrated Help page to guide in use of shortcodes and template tags
|
||||
|
||||
=Translations=
|
||||
|
||||
Available languages (in order of completeness):
|
||||
Japanese, Spanish, Danish, Czech, Hindi, Turkish, Dutch, French, Italian, German, Portuguese, Russian, Swedish, Finnish, Basque, Persian
|
||||
|
||||
Visit the [My Calendar translations site](http://translate.joedolson.com/projects/my-calendar) to check how complete a translation is.
|
||||
|
||||
Translating my plug-ins is always appreciated. Visit <a href="http://translate.joedolson.com">my translations site</a> to start getting your language into shape!
|
||||
|
||||
Translator Credits (in no particular order)*:
|
||||
|
||||
[Ale Gonzalez](http://60rpm.tv/i), [Outshine Solutions](http://outshinesolutions.com), [Jakob Smith](http://www.omkalfatring.dk/),, [globus2008](http://wordpress.org/support/profile/globus2008), Frederic Escallier, Luud Heck, Wim Strijbos, [Daisuke Abe](http://www.alter-ego.jp/), [Alex](http://blog.sotvoril.ru/), Mehmet Koçali, Uwe Jonas, Florian Edelmann, Efva Nyberg, [Sabir Musta](http://mustaphasabir.altervista.org), Massimo Sgobino, Leonardo Kfoury, Alexandre Carvalho, Amir Khalilnejad, [Aurelio De Rosa](http://www.audero.it/), Bayram Dede, Dani Locasati, Dario Nunez, Dirk Ginader, Evren Erten, Flávio Pereira, Francois-Xavier Benard, [Gianni Diurno](http://www.gidibao.net), Giksi, Heinz Ochsner, Kazuyuki Kumai, Liam Boogar, Maks, Mano, Massimo Sgobino, Mohsen Aghaei, Oscar, [Rashid Niamat](http://niamatmediagroup.nl/), Stefan Wikstrom, Thomas Meyer, Vedar Ozdemir, [Vikas Arora](http://www.wiznicworld.com), [Miriam de Paula](http://wpmidia.com.br), [HostUCan](http://www.hostucan.com), [Alex Alexandrov](http://www.webhostingrating.com), [Alyona Lompar](http://www.webhostinggeeks.com), [David Gil Pérez](http://www.sohelet.com), [Burkov Boris](http://chernobog.ru), [Raivo Ratsep](http://raivoratsep.com), [Jibo](http://jibo.ro), [Rasmus Himmelstrup](http://seoanalyst.dk), [kndb](http://blog.layer8.sh/)
|
||||
|
||||
* Translators may not have contributed to this plug-in; but have contributed to my [translation repository](http://translate.joedolson.com).
|
||||
|
||||
== Installation ==
|
||||
|
||||
1. Upload the `/my-calendar/` directory into your WordPress plugins directory.
|
||||
|
||||
2. Activate the plugin on your WordPress plugins page
|
||||
|
||||
3. Configure My Calendar using the following pages in the admin panel:
|
||||
|
||||
My Calendar -> Add/Edit Events
|
||||
My Calendar -> Manage Categories
|
||||
My Calendar -> Manage Locations
|
||||
My Calendar -> Settings
|
||||
My Calendar -> Style Editor
|
||||
My Calendar -> Behavior Editor
|
||||
My Calendar -> Template Editor
|
||||
|
||||
4. Edit or create a page on your blog which includes the shortcode [my_calendar] and visit
|
||||
the page you have edited or created. You should see your calendar. Visit My Calendar -> Help for assistance
|
||||
with shortcode options or widget configuration.
|
||||
|
||||
== Changelog ==
|
||||
|
||||
= 2.1.5 =
|
||||
|
||||
* Bug fix: upcoming events timestamps were converted to UTC.
|
||||
|
||||
= 2.1.4 =
|
||||
|
||||
* Bug fix: weekly view when crossing years jumped to next year
|
||||
* Bug fix: Upcoming events sorting fix
|
||||
* Bug fix: Upcoming events count fix
|
||||
* Bug fix: print stylesheet directory fix.
|
||||
|
||||
= 2.1.3 =
|
||||
|
||||
* Bug fix: My Calendar stripped title elements from singular posts unless an SEO plug-in was installed.
|
||||
|
||||
= 2.1.2 =
|
||||
|
||||
* Bug fix: Miscounted number of events in upcoming events view when events were multiple days.
|
||||
* Bug fix: My Calendar URL guessing now only selects from published Pages/posts
|
||||
* Tweak: Minor change to HTML output in print view
|
||||
* Added: Option to display current month or current year using Upcoming Events widget.
|
||||
* Added: Filter to display a custom <title> on single event details pages with settings field to configure that title. (Improves SEO)
|
||||
* Language updates: Italian, Russian, Basque
|
||||
|
||||
= 2.1.1 =
|
||||
|
||||
* Bug fix: users without 'Approve Event' ability submitted unapproved events even when event approval was disabled.
|
||||
|
||||
= 2.1.0 =
|
||||
|
||||
* Miscellaneous filepath fixes for custom icons
|
||||
* Fixed filepath issue for custom content directory in loading calendar generator
|
||||
* Added templating options to RSS feed event format
|
||||
* Added two new template tags: description_stripped and shortdesc_stripped; returns the description fields with HTML removed.
|
||||
* Re-organized settings to provide better grouping.
|
||||
* Removed jumpbox default setting; jumpbox now only configurable via shortcode.
|
||||
* Bug fix: titles missing in list view when open to details link enabled.
|
||||
* Bug fix: Multi-day events listed only once in upcoming events lists.
|
||||
* Minor stylesheet tweaks.
|
||||
|
||||
= 2.0.12 =
|
||||
|
||||
* I horribly screwed up the Upcoming Events widget in 2.0.11. Please accept my apologies.
|
||||
|
||||
= 2.0.11 =
|
||||
|
||||
* Fixed Broken custom stylesheets editing/selection.
|
||||
* Added Custom links for widget title links
|
||||
* Fixed issue with event links expiring immediately
|
||||
* Fixed issue with holiday collisions restricted in Upcoming Events/events only when holiday category is displayed.
|
||||
* Added full year output option for iCal downloads.
|
||||
* Added setting for calendar heading month formatting.
|
||||
* Updated language files: Japanese, Italian, German, Turkish
|
||||
|
||||
= 2.0.10 =
|
||||
|
||||
* Updated Japanese, Turkish, and Italian translations
|
||||
* Bug fix: Upcoming Events list could not be limited to a single author.
|
||||
* Bug fix: Un-approved events were being displayed in some public contexts.
|
||||
* Bug fix: Problem with RSS feed template elements not rendering in some cases.
|
||||
* Bug fix: Upcoming Events removed events inappropriately in certain situations when 'skip on holidays' was checked
|
||||
* Bug fix: Updated method for getting current plugin URL.
|
||||
* Deprecated support for WordPress versions before 3.0.6.
|
||||
|
||||
= 2.0.9 =
|
||||
|
||||
* Bug fix: Email notification on event addition to admin did not receive event data.
|
||||
* Bug fix: Accidentally eliminated weekend class. Now it's back!
|
||||
* Bug fix: Events crossing multiple dates need per-date unique IDs
|
||||
* Code change: Some code simplification for current URL and plugin URL references.
|
||||
* Updated languages: Portuguese, Dutch, Italian
|
||||
|
||||
= 2.0.8 =
|
||||
|
||||
* Re-written (simplified) holiday exclusion mechanism.
|
||||
* Performance improvements to templating and event processing.
|
||||
* Bug fix: Import from Kieran's "Calendar" plug-in was broken.
|
||||
* Bug fix: 'nextmonth' class was attached to events in weekly view; not appropriate to view.
|
||||
* Bug fix: Deleting single instance deleted entire event series.
|
||||
* Added option: number of events per page in admin events list
|
||||
|
||||
= 2.0.7 =
|
||||
|
||||
* Bug fix: Show list view on mobile devices option did not work.
|
||||
* Bug fix: No longer forcing links on titles in list or mini view.
|
||||
* Bug fix: All-day events came up with random end times.
|
||||
* Change: All-day checkbox added.
|
||||
* Change: All-day events automatically forced to hide end times.
|
||||
* Change: removed X-WR-CALNAME field from iCal output for improved compatibility
|
||||
* Updates: Partial updates to Spanish, Italian, and Dutch translations.
|
||||
|
||||
= 2.0.6 =
|
||||
|
||||
* Bug fix: Mini calendar links pointed to current display month regardless of current display date.
|
||||
* Bug fix: if day parameter was set, the main calendar views showed events for month starting from that date.
|
||||
* Bug fix: if day view was targeted from mini calendar with default cid parameter set, would not react
|
||||
* Bug fix: Calendar could not show events which had start and end dates which spanned the displayed period but were not included in the displayed period.
|
||||
* Moved screenshots into assets folder in version repository.
|
||||
* Translation source updated at http://translate.joedolson.com/ - now the translations need refreshing!
|
||||
|
||||
= 2.0.5 =
|
||||
|
||||
* Bug fix: Date links were eliminated in mini calendar if option to link to day-view was enabled.
|
||||
* Bug fix: Today's events drew events based on UTC instead of current timezone.
|
||||
|
||||
= 2.0.4 =
|
||||
|
||||
* Bug fix: template variable misassigned in the Today's Events shortcode.
|
||||
* Change: Added option to output iCal either in UTC or with times as entered. (Previously only UTC)
|
||||
|
||||
= 2.0.3 =
|
||||
|
||||
* Bug fix: Upcoming events widget did not support the "show_today's events" option correctly.
|
||||
* Bug fix: Was not possible to set 12:00 am as the end time for an event.
|
||||
* Bug fix: prevented blank title in main calendar due to faulty template.
|
||||
|
||||
= 2.0.2 =
|
||||
|
||||
* Bug fix: My Calendar did not enqueue jQuery
|
||||
* Bug fix: Grid view did not display last day of month if first day of week and last day of month were both Sunday
|
||||
|
||||
= 2.0.1 =
|
||||
|
||||
* Bug fix: Error in default settings for event titles.
|
||||
* Bug fix: Single Event iCal export broken
|
||||
* Bug fix: Today's Events shortcode broken if author not specified
|
||||
* Change: Deleting or updating categories now refreshes the cache.
|
||||
|
||||
= 2.0.0 =
|
||||
|
||||
* Completely re-written database model for events.
|
||||
* Added: pagination on event manager list of events.
|
||||
* Added: Restrict groups manager lists to currently grouped/ungrouped lists of events.
|
||||
* Added links to other event instances visible when editing events with multiple instances.
|
||||
* Added default category selection.
|
||||
* Added feature: limit calendar views by event author.
|
||||
* Added feature: filter event manager view by location, author, or category.
|
||||
* Added feature: mark categories as private, to only show those events to logged-in users.
|
||||
* Added templating to locations list so user can produce list of any set of location data.
|
||||
* Added option in event manager to copy location data into Locations table
|
||||
* Added [my_calendar_event] shortcode to fetch information for a single event.
|
||||
* Added template tag {timerange} to display start-end times.
|
||||
* Change: all events now have an end time. Option to hide end times to maintain current display.
|
||||
* Bug fix: iCal had missing newline; events now return labeled UTC time
|
||||
* Bug fix: RSS does better job of clearing non-XML special characters.
|
||||
* Bug fix: If preset location was selected, no other edits to locations could be done.
|
||||
* Bug fix: when copying an event, the new event was grouped in the same group as the source event.
|
||||
* Bug fix: if stylesheet was disabled, stylesheet was erased on next save of style settings.
|
||||
* Bug fix to category limiting which matched category names like 'baseball' to show 'all' categories.
|
||||
|
||||
= 1.11.3 =
|
||||
|
||||
* Fatal error in PHP 5.4+ https://bugs.php.net/bug.php?id=54657
|
||||
* Bug fix: {date} and {time} template tags not rendered in details link when run in a template.
|
||||
* Bug fix: upgrade database button placement off-screen
|
||||
* Bug fix: layout on stylesheet editor caused usability problems
|
||||
* Bug fix: added line break in iCal output.
|
||||
* Change: added alt attribute to category icons in appropriate contexts.
|
||||
* [My Calendar 2.0 beta](http://downloads.wordpress.org/plugin/my-calendar.2.0.0.zip) added to subversion repository. Here there be bugs.
|
||||
|
||||
= 1.11.2 =
|
||||
|
||||
* Bug fix: Called wp_editor on versions below 3.3
|
||||
* Bug fix: assorted PHP notices cleaned up.
|
||||
|
||||
= 1.11.1 =
|
||||
|
||||
* HTML validation issue fixed in calendar output.
|
||||
* Added option to hide display of external event links in calendar output.
|
||||
* Bug fix: Mini calendar should not toggle from mini view when main view switched.
|
||||
* Bug fix: Week time frame of list view did not return the 'no events' message.
|
||||
* Feature: No events message can be customized by using an enclosing shortcode: [my_calendar]No events this week![/my_calendar]
|
||||
|
||||
= 1.11.0 =
|
||||
|
||||
* Added option to use {date} in Today's Events widget title.
|
||||
* Events with the same time are now sub-sorted by title in Upcoming Events lists.
|
||||
* Template tag {endtime} returns empty string if same as start time
|
||||
* Standard event output returns empty string for event end time if same as start time.
|
||||
* Can only check 'multi-day event' option if event has multiple occurrences.
|
||||
* Categories in editor now sortable by either ID or category name.
|
||||
* Categories in input now sorted by category name.
|
||||
* Updated mobile detection class.
|
||||
* Major revision to permissions handling to use custom capabilities
|
||||
* Redesign of settings pages.
|
||||
* Can target tablet devices with CSS by adding a stylesheet called mc-tablet.css to your theme directory.
|
||||
* Can target other mobile devices with CSS by adding a stylesheet called mc-mobile.css to your theme directory.
|
||||
* Template tags now support before and after attributes: {tag before="<p>" after="</p>"}
|
||||
* Added option to retrieve events, categories, and locations from a remote database. (e.g., to share calendar information between 3 related sites.)
|
||||
* Eliminated details arrow; forcing anchor element on clickable title.
|
||||
* Added 'id' attribute to My Calendar shortcode, to customize unique ID for calendar and avoid non-compliant duplication of IDs
|
||||
* Added 'template' attribute to My Calendar shortcode, so specific calendars can use their own individual custom templates. Templates should be text files (.txt) placed in your theme directory.
|
||||
* Reduced specificity in stylesheets by eliminating ID-based references.
|
||||
* Fixed bug with day/date consistency in 5-day grid calendars.
|
||||
* Added day class to date boxes without dates.
|
||||
* Jumpbox is now switchable from the shortcode.
|
||||
* Fixed google maps link to use the correct directions targeting method
|
||||
* Various changes for WP 3.4 compatibility.
|
||||
* Updated Danish Translation
|
||||
* Updated Czech Translation
|
||||
* Added Hindi Translation
|
||||
|
||||
= 1.10.12 =
|
||||
|
||||
* Bug fix: List format showed all dates, regardless of whether there were events for that date.
|
||||
* Bug fix: List format showed incorrect classes.
|
||||
* Bug fix: Pipe separator for categories not supported with caching.
|
||||
* ARRRRGGGGHHHH!!! I'm sure you're as frustrated about all these little releases as I am. But who wants to sit on known bugs?
|
||||
|
||||
= 1.10.11 =
|
||||
|
||||
* Bug fix: Variable not checked for type threw usort warning.
|
||||
* Bug fix: Details links rendered incorrect page if linked from a single post location with permalinks not enabled.
|
||||
* Bug fix: Fixed bug where calendar returned no information if cache reached max size.
|
||||
* Settings change: Caching is now defaulted to off.
|
||||
|
||||
= 1.10.10 =
|
||||
|
||||
* Bug fix: Upcoming events list did not respect category limits.
|
||||
* Validation error/bug fix: Date for ID for first of month was incorrect.
|
||||
* Validation error: unencoded ampersand in iCal link if permalinks disabled.
|
||||
|
||||
= 1.10.9 =
|
||||
|
||||
* Added option to clear cache from settings.
|
||||
* Bug fix: Error in caching where cache returned false for multi-category limited calendars.
|
||||
* Bug fix: Error in caching where cache returned false for category limited calendars using category name as delimiter. Thanks to [Antti Palosaari](crope@iki.fi) for reporting this bug and for testing fixes.
|
||||
* Bug fix: Error notices if user is deleted who is assigned as host of some events. Thanks to Florian Edelmann for reporting this bug and contributing solution.
|
||||
* Bug fix: Upcoming events in dates mode returned null for cached dates.
|
||||
|
||||
= 1.10.8 =
|
||||
|
||||
* Bug fix: upcoming events list breaks if 'This is a multi-day event' is checked for an event with only a single occurrence.
|
||||
* Bug fix: Upcoming events caching did not cache correct data.
|
||||
* Modification: eliminated some extraneous database calls
|
||||
* Modified: clarifying text edits
|
||||
* Added: category classes on calendar date cells
|
||||
|
||||
= 1.10.7 =
|
||||
|
||||
* Made 'to' value in Google Maps links a translatable value.
|
||||
* Feature change: iCal download now respects currently selected month.
|
||||
* Added a phone number field to the Location manager
|
||||
* Added a setting to display only the core site's calendar on child sites in multisite mode.
|
||||
* Added a setting for the link target for mini calendar dates
|
||||
* Re-wrote labels for URL link target settings fields.
|
||||
* Bug fix: Location selector did not respect currently selected categories.
|
||||
* Bug fix: "Add another occurrence" option available in Edit mode, but not functional. Removed option.
|
||||
* Bug fix: Limiting by categories didn't trim whitespace from category names.
|
||||
* Bug fix: Fixed RSS/ICS/Print permalinks if PATHINFO permalinks are enabled.
|
||||
* Improved cache handling. Cache limit relative to amount of memory available to PHP. Cache stores information more efficiently.
|
||||
* Revised RSS/iCal handling to avoid .htaccess problems.
|
||||
|
||||
= 1.10.6 =
|
||||
|
||||
* Revised template tags so the description tags are run through wpautop(), and added _raw versions which are not.
|
||||
* Fixed a bug in URL generation so that URLs with ports are correctly constructed.
|
||||
* Fixed a bug iin Print output which did not allow restriction to multiple categories
|
||||
* Added option to use {date} in previous/next navigation links to indicate what date set is being navigated to.
|
||||
|
||||
= 1.10.5 =
|
||||
|
||||
* I made a truly bone-headed error in the last update, and I'm not even going to say what. If you didn't notice it, lucky for you!
|
||||
|
||||
= 1.10.4 =
|
||||
|
||||
* In my rush to fix the security issue, I broke an aspect of the event navigation. Apologies for this! Now fixed.
|
||||
|
||||
= 1.10.3 =
|
||||
|
||||
* Incorrectly called wp_kses(). Apologies for the frequent updates!
|
||||
|
||||
= 1.10.2 =
|
||||
|
||||
* Critical security update. Please upgrade promptly. Big thank you to Dean Batha for the bug report.
|
||||
|
||||
= 1.10.1 =
|
||||
|
||||
* Bug fix: undeclared array in widget manager
|
||||
* Renamed overly-generic constant.
|
||||
|
||||
= 1.10.0 =
|
||||
|
||||
* New feature: option to link dates in mini calendar to separate daily view instead of pop-up.
|
||||
* New feature: no longer necessary to manually edit behaviors in order to open main calendar event titles to separate page.
|
||||
* New feature: Ability to define grouped events as a single multi-day event and remove duplicates from events lists (upcoming events and today's events widgets)
|
||||
* New feature: group-association classes assigned to multi-day events in grid display.
|
||||
* New template tags: {daterange} and {multidate} for displaying a beginning and ending date range for a single event and for displaying each date in a multi-day event, respectively.
|
||||
* Week-view calendar caption now editable.
|
||||
* Added printable version.
|
||||
* Submit buttons in forms are now duplicated at top and bottom of long editing sections, to improve usability.
|
||||
* Minor style change to group editor to avoid group list colliding with editor textarea.
|
||||
* Removed angle brackets from Previous/Next events links.
|
||||
* Added custom action hooks for event save and event delete
|
||||
* Added ability to prevent today's events from showing up in upcoming events listings.
|
||||
* Added categories to iCal output.
|
||||
* iCal should return times in local time, not in UTC.
|
||||
* Bug fix: iCal output not correctly encoded
|
||||
* Bug fix: mc_next_link filter did not exist.
|
||||
* Bug fix: placed limit on maximum size of cached calendar data.
|
||||
* Bug fix: Upcoming events list will no longer occasionally display more items than expected.
|
||||
* Bug fix: menu icon not aware of custom content locations
|
||||
|
||||
= 1.9.8 =
|
||||
|
||||
* This is just a convenience update due to a warning appearing in 1.9.7 that I missed.
|
||||
|
||||
= 1.9.7 =
|
||||
|
||||
* Cache was not cleared when events were approved, rejected, or deleted.
|
||||
* Fixed bug with slashed characters in time and date formats
|
||||
* Fixed bug where previous/next links did not work on category pages
|
||||
* Fixed bug where event description was deleted if edited in groups manager.
|
||||
* Easydrag.js now respects conditional loading by page ID.
|
||||
* Small change to upcoming events list: events with an end time specifie and not crossing days will move off the list after they end rather than after they start.
|
||||
|
||||
= 1.9.6 =
|
||||
|
||||
* Fixed bug in Event Manager where information about whether an event was open for registration saved incorrectly.
|
||||
* Added raw details_link template tag.
|
||||
* Fixed Google Maps link error when using Long/Lat coordinates.
|
||||
* Associated image option was not available if HTML editor was enabled.
|
||||
|
||||
= 1.9.5 =
|
||||
|
||||
* Bug fix: Caching of Today's events did not account for category limits
|
||||
* Bug fix: Upcoming events listed by day duplication
|
||||
|
||||
= 1.9.4 =
|
||||
|
||||
* Bug fix: month-by-day recurring events in upcoming events list
|
||||
* Bug fix: duplication of events in upcoming events list
|
||||
* Bug fix: when editing a single event with indefinite recurrences, future events set up without continuing recurrence.
|
||||
* Function error when data not present fixed.
|
||||
* Added display of sending name/address for support messages
|
||||
|
||||
= 1.9.3 =
|
||||
|
||||
* Stylesheet saving can write longer files. Solves problem with occasional truncation of stylesheets.
|
||||
* Added transient caching for calendar events to improve performance, plus other various performance improvements
|
||||
* Small html output change.
|
||||
* 1.9.0 made details boxes draggable; made this optional.
|
||||
* Added plug-in support request form.
|
||||
* Added updated French translation to 1.9.2
|
||||
* Fixed bug with date switcher duplicating/skipping months.
|
||||
* Updated User's Guide (not included with plug-in)
|
||||
|
||||
= 1.9.2 =
|
||||
|
||||
* Bug fix: Fixed sort error returned by calendar if no events are in array.
|
||||
* Bug fix: Fixed incorrect URLs for icons in custom directory in category key.
|
||||
* Bug fix: Caption text did not display.
|
||||
* Added {date} and {time} to details link text templating.
|
||||
* Bug fix: Fixed {icon} URL in template output.
|
||||
* Bug fix: Fixed bug with table layout of dates when weekends are disabled on grid calendar.
|
||||
* Bug fix: Fixed bug with generation of details link when not using permalinks.
|
||||
* Bug fix: Fixed bug with HTML editor converting HTML entities.
|
||||
* Bug fix: Fixed bug where weekly view showed the wrong dates if the current week started in the previous month.
|
||||
|
||||
= 1.9.1 =
|
||||
|
||||
* Bug fix: Incorrect title template tag auto-generated if title template is empty.
|
||||
* Bug fix: Create events permissions broken
|
||||
* Bug fix: Host list broken in WordPress versions lower than 3.1
|
||||
* Bug fix: My Calendar not using WordPress defaults for customizable date and time settings if not set by user.
|
||||
* Bug fix: Turning off calendar icons did not turn off icons in key
|
||||
* Bug fix: details links used current URL instead of stored URL
|
||||
* Bug fix: default widget settings not loaded on upgrade.
|
||||
* Bug fix: next/previous links not working on home page if permalinks not set.
|
||||
* Bug fix: event title shown in date field in list mode was not for the first event of the day.
|
||||
* Style change: Minor change to my-calendar.css to adjust for the green background on weekends. (Which showed up as the result of a fix to an HTML problem in 1.8.9.)
|
||||
* Bug fix/Option add: Added option to remove individual iCal link
|
||||
* Option add: Added option to conceal first event title/number of events with date in list mode.
|
||||
|
||||
= 1.9.0 =
|
||||
|
||||
Additions:
|
||||
|
||||
* template editing for list, grid, mini, and single event output.
|
||||
* pop-up box is now draggable.
|
||||
* date format option for grid mode, week view.
|
||||
* templating for details link text.
|
||||
* templating for event URL link text.
|
||||
* location filtering from shortcode.
|
||||
* image upload option for events
|
||||
* day class to calendar date headings and cells
|
||||
* individual instances of repeating events can be edited
|
||||
* feature to add multiple occurrences of an event simultaneously. (concept from Dave Heitzman)
|
||||
* feature to mass edit information for groups of events (concept from Dave Heitzman)
|
||||
* stored URL for locations (contrib by John Colvin)
|
||||
* recurring daily events on weekdays only (based on contrib by John Colvin)
|
||||
* optional templating for all event output formats
|
||||
* individual event occurrence iCal export
|
||||
* numerous additional template tags
|
||||
* Option to use custom location filter fields as data control
|
||||
* Shortcode to generate list of saved locations
|
||||
* Network administrators can control whether sub-site calendars contribute only to a central calendar, only to their own calendar, or whether site administrators can make that choice.
|
||||
* Upgrade notice information in dashboard for future upgrades.
|
||||
* implementation of WordPress text diff to compare your styles and scripts against my current released versions
|
||||
* Option to skip a defined number of events in upcoming events lists.
|
||||
|
||||
Bug fixes:
|
||||
|
||||
* jump box was displaying in week/grid view.
|
||||
* some potentially repeatable IDs (code validation).
|
||||
* 'Administrators see all options' did not work.
|
||||
* Fixed timestamps on main calendar objects
|
||||
* Squashed e_notice errors.
|
||||
* category limiting did not work without permalinks due to GET variable conflict with WordPress core
|
||||
* Missing nonce in database upgrade routine
|
||||
* Mini calendar simultaneously displayed single event view when visited.
|
||||
* Link generation for details view did not work if calendar link parameterized
|
||||
* Issue with weekdays only calendar if day of week set to start on Sunday
|
||||
* Issue with retrieval of user-specific settings
|
||||
* Issue with accessing styles and javascript if My Calendar installed in non-standard directory.
|
||||
* Problem in Today's Events widget when Holiday restrictions are enabled.
|
||||
|
||||
Changes:
|
||||
|
||||
* replaced all default icons with 24-bit transparent PNGs
|
||||
* jumpbox output to automatically scope to the oldest dates in the database.
|
||||
* iCal output changed to output all events for complete current month
|
||||
* RSS output to prioritze newly added events
|
||||
* holiday skipping/fifth week customization moved into event manager function
|
||||
* new 'close' icon for pop-up box; added close icon and scripting to mini calendar pop-up
|
||||
* copy in several places; updated template tags.
|
||||
* location lists sorted by location label (contrib by John Colvin)
|
||||
* Eliminated calendar heading option
|
||||
* default style resets no longer stored in global variables, instead stored as files.
|
||||
* Map links now trigger the driving directions dialog in Google Maps
|
||||
* New default stylesheet, refresh.css
|
||||
|
||||
= 1.8.9 =
|
||||
|
||||
* Fixed bug with database upgrade in multi-user additional calendars
|
||||
* Fixed bug where calendar picked up current month labeling using current day of the month
|
||||
* Added French translation
|
||||
|
||||
= 1.8.8 =
|
||||
|
||||
* Fixed bug in locations filtering that disabled feature if user not logged in.
|
||||
* Re-arranged settings and added notices about options which will be removed in a future release.
|
||||
* Revised RSS feed to use event permalinks when they are available.
|
||||
|
||||
= 1.8.7 =
|
||||
|
||||
* One very minor change in 1.8.6 caused some plug-in conflicts, so I rolled that change back. Will find another solution to the problem it solved. This change affects very few users.
|
||||
|
||||
= 1.8.6 =
|
||||
|
||||
* Fixed bug with {details} template tag when Upcoming widgets configured as Events
|
||||
* Location and category filters now do not display forms/lists if there isn't more than one choice.
|
||||
* Extended details link feature to main calendar output and added to output options.
|
||||
* Minor changes to time-entry jQuery plug-in to improve usability.
|
||||
* Updated Japanese translation to 1.8.5
|
||||
* Added Russian translation to 1.8.5
|
||||
|
||||
= 1.8.5 =
|
||||
|
||||
* Another bug fix to monthly-by-day recurrence.
|
||||
* Fixed minor problem with default template not being visible in widget.
|
||||
* Fixed 'widget title linked' bug.
|
||||
* Added Turkish translation by Mehmet Ko&231;ali
|
||||
|
||||
= 1.8.4 =
|
||||
|
||||
* Mini calendar widget had a mis-labeled option field
|
||||
* Custom User settings for event region didn't function correctly.
|
||||
* A variety of bug fixes applied to events repeating on a monthly-by-day basis
|
||||
|
||||
= 1.8.3 =
|
||||
|
||||
* Turned on spam flag toggle, which I had commented out and failed to restore...
|
||||
* Default return false ('not spam') for privileged users when checking Akismet
|
||||
|
||||
= 1.8.2 =
|
||||
|
||||
* Fixed bug with {icon} template tag, for real.
|
||||
* Fixed RSS missing argument
|
||||
* Fixed empty list rendering in upcoming events widget
|
||||
|
||||
= 1.8.1 =
|
||||
|
||||
* Fixed bug with region saving on edit of location
|
||||
* Fixed bug with single-event view receiving date as array
|
||||
* Fixed bug with {icon} template tag
|
||||
* Fixed bug with calendar output if user settings are enabled but not applied by user
|
||||
* Fixed bug with list/grid format toggle
|
||||
* Fixed bug with upcoming events limited by category names
|
||||
|
||||
= 1.8.0 =
|
||||
|
||||
* Added event region as a location field
|
||||
* Added time selector and altered calendar range selector.
|
||||
* Added visual editor for event description textarea.
|
||||
* Added templating tag to add a link to the single event view.
|
||||
* Added option to not display weekends in grid format.
|
||||
* Added unique ID for each event in calendar.
|
||||
* Added default sort order option for admin events list.
|
||||
* Added admin events list to screen while editing or copying event.
|
||||
* Added shortcode generator for Page and Post editor.
|
||||
* Added spam protection: New events are now checked through Akismet if installed and configured.
|
||||
* Added category selection shortcode.
|
||||
* Added mini calendar widget.
|
||||
* Added external link class.
|
||||
* Added list/grid view toggle.
|
||||
* Added mobile detection so mobile devices receive list format without JavaScript for easier reading.
|
||||
* Added Upcoming Events widget sort order option.
|
||||
* Added Option to link widget title to main calendar page.
|
||||
* Change: Minor reorganization of settings page.
|
||||
* Change: Altered time input to use non-military format time, added JavaScript time input.
|
||||
* Change: Moved My Calendar menu items into the content menu.
|
||||
* Change: When calendar is limited by categories, only the displayed categories are listed in the category key.
|
||||
* Change: If widget title is left blank, widget will have no title.
|
||||
* Change: Moved translation files into a subdirectory (/lang/)
|
||||
* Bug fix: hcal dates
|
||||
* Bug fix: problem where restoring styles referenced out of date styles
|
||||
* Bug fix: error in primary stylesheet
|
||||
* Bug fix: issue with month-by-day recurring events when recurrance set at 0
|
||||
* Bug fix: issue with end dates when recurrance set at 0
|
||||
* Bug fix: DB installed to match WPDB chararacter set and collation.
|
||||
* Bug fix: turn-of-year page navigation in week view.
|
||||
* Bug fix: entries not remembered in error condition post
|
||||
* Updated German Translation to version 1.7.0 (Christopher Schauer)
|
||||
* Updated German Translation to version 1.7.8 (Uwe Jonas)
|
||||
* Note: during this update cycle, I received two German translations, and am using the most up to date version.
|
||||
* Added Swedish Translation to version 1.7.8
|
||||
|
||||
= 1.7.8 =
|
||||
|
||||
* Bug fix: Behaviors page limits lost on settings refresh
|
||||
* Bug fix: Fix {enddate} shortcode output.
|
||||
* Bug fix: iCal output improvements
|
||||
* Modification: RSS and iCal output are disabled entirely when turned off, rather than just hidden.
|
||||
* Modification: Added styles for days out of current month
|
||||
|
||||
= 1.7.7 =
|
||||
|
||||
* Bug fix: Upcoming Events widget fault in 'dates' mode.
|
||||
|
||||
= 1.7.6 =
|
||||
|
||||
* Bug fix: Upcoming Events widget in days mode was not offsetting time using GMT reference. (Committed silently in 1.7.5)
|
||||
* Bug fix: Default template not rendered in Today's Events when template left blank
|
||||
* Bug fix: Slashes not stripped in category key.
|
||||
* Bug fix: Upcoming Events widget if no upcoming events
|
||||
* Bug fix: Error with retrieval of Author's ID
|
||||
* Fixed some non-translatable text strings
|
||||
* Logic change: Upcoming Events now bases choice on time rather than date (events happening later today are future, rather than only events happening tomorrow or later.)
|
||||
* Enhancement: respects custom wp-content location definitions
|
||||
|
||||
= 1.7.5 =
|
||||
|
||||
* Bug fix: Error with upcoming events when selected by dates and holiday skipping enabled.
|
||||
* Bug fix: Upcoming Events widget title defaulted to 'Today's Events'
|
||||
* Change: Reversed order of Latitude/Longitude on forms to match Google's implementation.
|
||||
|
||||
= 1.7.4 =
|
||||
|
||||
* Bug fix: Upcoming events templates ran htmlentities on output
|
||||
|
||||
= 1.7.3 =
|
||||
|
||||
* Bug fix: upcoming events substitute text still not appearing in some contexts.
|
||||
* Bug fix: Today's event substitute text had assignment in place of comparison
|
||||
* Bug fix: Event location not saved properly on edit if Location Fields are disabled on input
|
||||
* Bug fix: Fixed date and time issues in iCal output
|
||||
* Bug fix: Fixed character set issue in RSS output
|
||||
* Bug fix: Major problem with Holiday category event delimiting
|
||||
* Danish translation updated to 1.7.0
|
||||
* Japanese translation updated to 1.7.1
|
||||
* Minor documentation and readme.txt updates
|
||||
* Added additional fallback settings for widgets
|
||||
* Fixed minor installation issue with version detection.
|
||||
* Added CSS hook .nextmonth on dates occurring past the end of the currently displayed month.
|
||||
* Added check for '#' symbol on hex colors in category management.
|
||||
|
||||
= 1.7.2 =
|
||||
|
||||
* Bug fix: Fixed import from Calendar feature.
|
||||
* Bug fixed: Upcoming events widget default text fixed
|
||||
* Italian translation updated to 1.7.0
|
||||
|
||||
= 1.7.1 =
|
||||
|
||||
* Default setting for custom user location type not set
|
||||
* Reset for inherit.css styles missing
|
||||
* Widget shortcodes stripped HTML
|
||||
* Added a fallback function for exif_imagetype 'cuz some servers don't have it available by default.
|
||||
* Nonce missing in database upgrade
|
||||
* Ability to edit text for shortcode fallback (No events text) lost.
|
||||
* Widget defaults not installed on new installation
|
||||
* Mini and List jQuery did not prevent default link action
|
||||
* Changed install action to default User settings to off.
|
||||
|
||||
= 1.7.0 =
|
||||
|
||||
* Fix in AJAX navigation for IE
|
||||
* Fix in JavaScript to re-activate close button
|
||||
* Fixed bug with locations list not registering current location type in form mode
|
||||
* Fixed bug with upcoming events and today's events output when regions limits were set
|
||||
* Fixed bug with upcoming events producing incorrect dates for events recurring on a specific day of the month.
|
||||
* Revision of Widgeting setup to offer multi-widget support (will require you to re-setup your widgets)
|
||||
* Revision of style editor to use external stylesheets.
|
||||
* Revision of style support to add option for custom stylesheets stored outside of plugin directory
|
||||
* Added: multiple base stylesheets
|
||||
* Added: Event markup in hCal format
|
||||
* Added Weekly mode for list and grid view
|
||||
* Added RSS and iCal exports for upcoming events (enable and disable in settings)
|
||||
* Added option to block display of an event if there is an event that day which is in a designated 'Holiday' category.
|
||||
* Added permission setting to allow non-administrators to edit or delete any event.
|
||||
* Added Czech translation (to 1.6.3)
|
||||
* Updated Italian and Danish translations
|
||||
* Security: Implemented nonces
|
||||
|
||||
= 1.6.3 =
|
||||
|
||||
* Updated jQuery to fix conflicts in previous versions and so behaviors would work with AJAX navigation. Not updated by upgrade; use Behaviors reset to apply.
|
||||
* Incorporated option to enable AJAX navigation for next/previous navigation.
|
||||
* Fixed bug with multi-month display in list format where January could not be displayed.
|
||||
* Revised settings page for clarity.
|
||||
* Fixed some default settings issues.
|
||||
* Fixed a bug where the locations lists didn't respect the datatype parameter.
|
||||
* Added templating to event titles for calendar grid or list output.
|
||||
|
||||
= 1.6.2 =
|
||||
|
||||
* Fixed broken style editor. (The way it was broken was awfully weird...kinda wonder how I did it!)
|
||||
* Fixed missing div in calendar list output.
|
||||
* Removed debugging call which had been left from testing.
|
||||
* Fixed storage of initial settings for user settings (array did not store probably initially.)
|
||||
* Added Italian translation by [Sabir Musta](http://mustaphasabir.altervista.org)
|
||||
|
||||
= 1.6.1 =
|
||||
|
||||
* Bug fix in event saving
|
||||
|
||||
= 1.6.0 =
|
||||
|
||||
* Feature: User profile defined time zone preference
|
||||
* Feature: User profile defined location preference
|
||||
* Feature: Define event host as separate from event author
|
||||
* Feature: Added ability to hide Prev/Next links as shortcode attribute
|
||||
* Change: Separated Style editing from JS editing
|
||||
|
||||
= 1.5.4 =
|
||||
|
||||
* Fixed: Bug with permissions in event approval process.
|
||||
|
||||
= 1.5.3 =
|
||||
|
||||
* Fixed: Bug which broke the {category} template tag
|
||||
* Fixed: Bug which moved extra parameters before the "?" in URLs
|
||||
* Fixed: Bug which produced an incorrect date with day/month recurring events on dates with no remainder
|
||||
* Added: Japanese translation by [Daisuke Abe](http://www.alter-ego.jp/)
|
||||
|
||||
= 1.5.2 =
|
||||
|
||||
* Fixed: Bug where event data wasn't remembered if an error was triggered on submission.
|
||||
|
||||
= 1.5.1 =
|
||||
|
||||
* Fixed: Bug where events recurring monthly by days appeared on wrong date when month begins on Sunday.
|
||||
* Fixed: Bug where events recurring monthly by days appeared on dates prior to the scheduled event start.
|
||||
* Performance improvement: Added SQL join to incorporate category data in event object
|
||||
* Added quicktag to provide access to category color and icon in widget templates
|
||||
* Changed link expiration to be associated with the end date of events rather than the beginning date.
|
||||
* Updated readme plugin description, help files, and screenshots.
|
||||
|
||||
= 1.5.0 =
|
||||
|
||||
* Added: German translation.
|
||||
* Updated: Danish translation.
|
||||
* Added: Administrator notification by email feature [Contributions by Roland]
|
||||
* Added: Reservations and Approval system for events. [Contributions by Roland]
|
||||
* Added: Events can be recurring on x day of month, e.g. 3rd Monday of the month.
|
||||
|
||||
= 1.4.10 =
|
||||
|
||||
* Fixed: Failed to increment internal version pointer in previous version.
|
||||
* Fixed: Invalid styles created if category color set to default.
|
||||
* Fixed: (Performance) Default calendar view attempted to select invalid category.
|
||||
* Updated: Danish translation.
|
||||
|
||||
= 1.4.9 =
|
||||
|
||||
* Fixed: Bug where location edits couldn't be saved if location fields were on and dropdown was off
|
||||
* Fixed: Bug where latitude and longitude were switched on Google Maps links
|
||||
* Fixed: Bug where map link would not be provided if no location data was entered except Lat/Long coordinates.
|
||||
|
||||
= 1.4.8 =
|
||||
|
||||
* Added: Ability to copy events to create a new instance of that event
|
||||
* Added: Customization of which input elements are visible separate from what output is shown.
|
||||
* Fixed: Issue where one JS element could not be fully disabled
|
||||
* Fixed: Internationalization fault with Today's Events showing events from previous day
|
||||
* Fixed some assorted text errors and missing internationalization strings.
|
||||
* Fixed issue where the 'Help' link was added to all plug-in listings.
|
||||
* Reorganized settings page UI.
|
||||
|
||||
= 1.4.7 =
|
||||
|
||||
* Fixed: Bug where infinitely recurring events whose first occurrence was in the future were not rendered in upcoming events
|
||||
* Fixed: Bug where infinitely recurring bi-weekly events only rendered their first event in calendar view
|
||||
* Added: Option to indicate whether registration for an event is open or closed, with customizable text.
|
||||
* Added: Option to supply a short description alternative to the full description.
|
||||
|
||||
= 1.4.6 =
|
||||
|
||||
* Fixed: Flash of unstyled content prevention scripts weren't disabled when other scripting was disabled.
|
||||
* Fixed: Categories which started with numerals couldn't have custom styles.
|
||||
* Fixed: Locations required valid 0 float value to save records on some servers; now supplied by default.
|
||||
|
||||
= 1.4.5 =
|
||||
|
||||
* Fixed a bug with editing and adding locations
|
||||
* Fixed a bug with error messages when adding categories
|
||||
* Fixed a bug with identification of current day (again?)
|
||||
* Added Danish translation (Thanks to Jakob Smith)
|
||||
|
||||
= 1.4.4 =
|
||||
|
||||
* Fixed a bug where event end times tags were not rendered when blank in widget templates
|
||||
* Fixed a bug with event adding and updating for Windows IIS
|
||||
* Fixed a bug with international characters
|
||||
* Reduced number of SQL queries made.
|
||||
* Moved JavaScript output to footer.
|
||||
* Improved error messages.
|
||||
* Significant edits to basic codebase to improve efficiency.
|
||||
* Fixed bug where full default styles didn't initially load on new installs.
|
||||
* Re-organized default styles to make it easier for users to customize colors.
|
||||
|
||||
= 1.4.3 =
|
||||
|
||||
* Fixed a bug where event end times were displaying the start time instead when editing.
|
||||
* Fixed a bug introduced by the mini calendar option which displayed titles twice in list format.
|
||||
* Fixed a bunch of typos.
|
||||
* Added a loop which automatically adds the mini calendar styles if you don't already have them.
|
||||
* Fixed a bug where JS didn't run if the 'show only on certain pages' option was used.
|
||||
* Added a qualifier for upgrading databases when you haven't added any events.
|
||||
|
||||
= 1.4.2 =
|
||||
|
||||
* Fixed a bug in the widget display code which caused problems displaying multiple categories.
|
||||
|
||||
= 1.4.1 =
|
||||
|
||||
* Database upgrade didn't run for some users in 1.4.0. Added manual check and upgrade if necessary.
|
||||
|
||||
= 1.4.0 =
|
||||
|
||||
* Bug fixed: Today's Events widget was not taking internationalized time as it's argument
|
||||
* Added end time field for events
|
||||
* Added option for links to expire after events have occurred.
|
||||
* Added options for alternate applications of category colors in output.
|
||||
* Added ability to use My Calendar shortcodes in text widgets.
|
||||
* Added GPS location option for locations
|
||||
* Added zoom selection options for map links
|
||||
* Lengthened maximum length for category and event titles
|
||||
* Added a close link on opened events details boxes.
|
||||
* Added an option for a mini calendar display type in shortcode
|
||||
* Optimized some SQL queries and reduced total number of queries significantly.
|
||||
* Extended the featured to show CSS only on certain pages to include JavaScript as well.
|
||||
* Upcoming events widget only allowed up to 99 events to be shown forward or back. Changed to 999.
|
||||
* Attempted to solve a problem with infinitely recurring events not appearing in upcoming events. Let me know.
|
||||
* Added setting to change Previous Month/Next Month text.
|
||||
* Yeah, that's enough for now.
|
||||
|
||||
= 1.3.8 =
|
||||
|
||||
* Fixed problem with CSS editing which effectively disabled CSS unless a specific choice had been made for pages to show CSS
|
||||
|
||||
= 1.3.7 =
|
||||
|
||||
* Aren't you enjoying the daily upgrades? I made a mistake in 1.3.5 which hid text in an incorrect way, causing problems in some contexts.
|
||||
|
||||
= 1.3.6 =
|
||||
|
||||
* Fixed an issue where not having defined Pages to show CSS resulted in a PHP warning for some configs.
|
||||
|
||||
= 1.3.5 =
|
||||
|
||||
* Fix for flash of unstyled content issue.
|
||||
* Added configuration for time text on events with non-specific time.
|
||||
* Fixed bug where, in list views with multiple months, events occurring on days which did not exist in the previous month were not rendered. (Such as March 30th where previous month was February.)
|
||||
* Fixed bug where the multi-month view setting for lists caused previous/next events buttons to skip months in calendar view.
|
||||
* Added option to disable category icons.
|
||||
* Added option to insert text in calendar caption/title area, appended to the month/year information.
|
||||
* Fixed a bug where it was not possible to choose the "Show by days" option in the upcoming events widget.
|
||||
* Updated documentation to match
|
||||
* Fixed a bug where upcoming events in Days mode did not display correct date
|
||||
* Added an option to define text to be displayed in place of Today's Events widget if there are no events scheduled.
|
||||
* Minor changes to default CSS
|
||||
* Ability to show CSS and JavaScript only on selected pages.
|
||||
|
||||
= 1.3.4 =
|
||||
|
||||
* Fixed a bug with map link and address display which I forgot to deal with in previous release.
|
||||
|
||||
= 1.3.3 =
|
||||
|
||||
* Fixed bug with upgrade path which caused locations database to be created on every activation (also cause of errors with some other plugins). (Thanks to Steven J. Kiernan)
|
||||
* Made clone object PHP 4 compatible (Thanks to Peder Lindkvist)
|
||||
* Corrected errors in shortcode functions for today's events
|
||||
* Corrected rendering of non-specific time events as happening at midnight in widget output
|
||||
|
||||
= 1.3.2 =
|
||||
|
||||
* Fixed bugs with unstripped slashes in output
|
||||
* Fixed a bug where users could not add location information in events if they had not added any recurring locations
|
||||
* Removed requirement that address string must be five characters to display a link
|
||||
|
||||
= 1.3.1 =
|
||||
|
||||
* Corrected incorrect primary key in upgrade path.
|
||||
* Added version incrementing in upgrade path.
|
||||
|
||||
= 1.3.0 =
|
||||
|
||||
* Fixed a CSS class which was applied to an incorrect element.
|
||||
* Revisions to the Calendar import methods
|
||||
* Moved style editing to its own page
|
||||
* Added JavaScript editing to allow for customization of jQuery behaviors.
|
||||
* Internationalized date formats
|
||||
* Shortcode support for multiple categories.
|
||||
* Shortcode support for custom templates in upcoming and today's events
|
||||
* Added a settings option to eliminate the heading in list format display.
|
||||
* Fixed a bug which treated the event repetition value as a string on event adding or updating, not allowing some users to use '0' as an event repetition.
|
||||
* Made events listing sortable in admin view
|
||||
* Minor revisions in admin UI.
|
||||
* Added database storage for frequently used venues or event locations.
|
||||
* Modified JavaScript for list display to automatically expand events scheduled for today.
|
||||
|
||||
= 1.2.1 =
|
||||
|
||||
* Corrected a typo which broke the upcoming events widget.
|
||||
|
||||
= 1.2.0 =
|
||||
|
||||
* Added shortcodes to support inserting upcoming events and todays events lists into page/post content.
|
||||
* Added option to restrict upcoming events widgets by category
|
||||
* More superficial CSS changes
|
||||
* Added Brazilian Portuguese language files
|
||||
* Fixed bug where I reversed the future and past variable values for upcoming events widgets
|
||||
* Fixed bug in multi-user permissions.
|
||||
* Added feature to look for a custom location for icons to prevent overwriting of custom icons on upgrade.
|
||||
|
||||
= 1.1.0 =
|
||||
|
||||
* Fixed some problems with Upcoming Events past events not scrolling off; hopefully all!
|
||||
* Fixed some problems with fuzzy interpretations of the numbers of past/future events displayed in Upcoming Events.
|
||||
* Added Bi-weekly events
|
||||
* Added restrictions so that admin level users can edit any events but other users can only edit their own events
|
||||
* Removed character restrictions on event titles
|
||||
* Revised default stylesheet
|
||||
|
||||
= 1.0.2 =
|
||||
|
||||
* Fixed problems with editing and deleting events or categories in multiblog installation
|
||||
* Fixed escaping/character set issue
|
||||
* Fixed issue when blog address and wp address did not match (introduced in 1.0.1)
|
||||
* Added import method to transfer events and categories from Kieran O'Shea's Calendar plugin
|
||||
|
||||
= 1.0.1 =
|
||||
|
||||
* Added missing template code for event end dates.
|
||||
* Changed defaults so that styles and javascript are initially turned on.
|
||||
* Removed function collisions with Calendar
|
||||
* Fixed bug where My Calendar didn't respect the timezone offset in identifying the current day.
|
||||
* Fixed bug where multiblog installations in WP 3.0 were unable to save events and settings.
|
||||
* Added Spanish translation, courtesy of [Esteban Truelsegaard](http://www.netmdp.com). Thanks!
|
||||
|
||||
= 1.0.0 =
|
||||
|
||||
* Initial launch.
|
||||
|
||||
== Frequently Asked Questions ==
|
||||
|
||||
= Hey! Why don't you have any Frequently Asked Questions here! =
|
||||
|
||||
Because the majority of users end up on my web site asking for help anyway -- and it's simply more difficult to maintain two copies of my Frequently Asked Questions. Please visit [my web site FAQ](http://www.joedolson.com/articles/my-calendar/faq/) to read my Frequently Asked Questions!
|
||||
|
||||
= This plug-in is really complicated. Why can't you personally help me figure out how to use it? =
|
||||
|
||||
I can! Just not in person. I've written a User's Guide for My Calendar, which you can [purchase at my web site](https://www.joedolson.com/articles/my-calendar/users-guide/) for $23. ($19 if you're not interested in getting updates.) This helps defray the thousand plus hours I've spent in developing the plug-in and providing support. Please, consider buying the User's Guide or [making a donation](https://www.joedolson.com/donate.php) before asking for support!
|
||||
|
||||
= How can visitors to my site submit events? =
|
||||
|
||||
I've written a paid plug-in that adds this feature to My Calendar, called My Calendar: Submissions. You can [buy it at my web site](https://www.joedolson.com/articles/my-calendar/submissions/)!
|
||||
|
||||
== Screenshots ==
|
||||
|
||||
1. Calendar using calendar list format.
|
||||
2. Calendar using monthly calendar format.
|
||||
3. Event management page
|
||||
4. Category management page
|
||||
5. Settings page
|
||||
6. Location management
|
||||
7. Style editing
|
||||
8. Mini calendar
|
||||
9. Script/behavior editing
|
||||
10. Template editing
|
||||
|
||||
== Upgrade Notice ==
|
||||
|
||||
= 2.0.0 =
|
||||
Major database redesign. Some new features, including single event view and pagination in events lists. Database update is non-destructive; no data will be deleted.
|
||||
@@ -0,0 +1,843 @@
|
||||
=== NextGEN Gallery ===
|
||||
Contributors: photocrati
|
||||
Tags:gallery,image,images,photo,photos,picture,pictures,slideshow,flash,media,thumbnails,photo-albums,nextgen-gallery,nextgen
|
||||
Requires at least: 3.6.1
|
||||
Tested up to: 4.0
|
||||
Stable tag: trunk
|
||||
License: GPLv2
|
||||
|
||||
The most popular WordPress gallery plugin and one of the most popular plugins of all time with over 10 million downloads.
|
||||
|
||||
== Description ==
|
||||
|
||||
= WordPress Gallery Plugin =
|
||||
|
||||
NextGEN Gallery is the most popular **WordPress gallery plugin**, and one of the most popular WordPress plugins of all time, with over 10 million downloads.
|
||||
|
||||
It provides a powerful engine for uploading and managing galleries of images, with the ability to batch upload, import meta data, add/delete/rearrange/sort images, edit thumbnails, group galleries into albums, and more. It also provides two front-end display styles (slideshows and thumbnail galleries), both of which come with a wide array of options for controlling size, style, timing, transitions, controls, lightbox effects, and more.
|
||||
|
||||
*The NextGEN Gallery WordPress gallery plugin is now proudly maintained by <a href='http://www.photocrati.com'>Photocrati Media</a>. Special thanks to Alex Rabe who created and maintained NextGEN from 2007 through 2011.*
|
||||
|
||||
**NEXTGEN GALLERY 2.0: MAJOR UPDATE IN JULY 2013.** *We released a major update and overhaul to NextGEN Gallery in July 2013. NextGEN Gallery 2.0 presents a completely reworked interface, both for the central options panel and for adding galleries to pages and posts. It's dramatically more powerful and flexible.*
|
||||
|
||||
**INTRODUCING NEXTGEN GALLERY PRO.** *Along with NextGEN 2.0, we're happy to announce a "Pro" upgrade to NextGEN. NextGEN Pro offers 6 new gallery displays, including Pro Masonry, Pro Filmstrip, Pro Film, Pro Thumbnail Grid, Pro Slideshow, and Pro Blogstyle galleries. It also includes a responsive, fullscreen, mobile-friendly Pro Lightbox with commenting and social sharing for individual images within galleries. And it includes premium one-on-one email support for both NextGEN Gallery and NextGEN Pro.*
|
||||
|
||||
**<a href="http://www.nextgen-gallery.com/nextgen-pro">LEARN MORE ABOUT NEXTGEN PRO</a>**
|
||||
|
||||
|
||||
= NextGEN WordPress Gallery Plugin Features =
|
||||
|
||||
|
||||
*Upload Galleries*
|
||||
|
||||
* Our WordPress gallery plugin offers diverse and powerful functionality for getting images from your desktop to your website. You can easily upload batches of images via a standard WordPress-style uploader, or upload images via zip file or FTP. NextGEN will automatically import your images meta data.
|
||||
|
||||
*Manage Galleries*
|
||||
|
||||
* Centralized gallery management. Enjoy a single location where you can see and manage all your galleries.
|
||||
* Edit galleries. Add or exclude images, change gallery title and description, reorder of images, resize thumbnails.
|
||||
* Thumbnail Management. Turn thumbnail cropping on and off, customize how individual thumbnails are cropped, and bulk resize thumbnails across one or more galleries.
|
||||
* Edit Individual Images. Edit meta data and image tags, rotate images, and exclude images.
|
||||
* Watermarks. Quickly add watermarks to batches or galleries of images.
|
||||
* Albums. Create and organize collections of galleries, and display them in either compact or extended format.
|
||||
|
||||
*Display Galleries*
|
||||
|
||||
* Multiple Gallery Types. Choose between two main display styles: Slideshow and Thumbnail, and allow visitors to toggle between the two. Or display Imagebrowser galleries and Singlepics.
|
||||
* Slideshow Galleries. Choose from a vast array of options for slideshows, including slideshow size, transition style, speed, image order, and optional navigation bar.
|
||||
* Thumbnail Galleries. Choose from a wide range of options to customize thumbnail galleries, including 5 different lightboxes for individual images, optional thumbnail cropping and editing, thumbnail styles, captions, and more.
|
||||
* Single Image Displays. Display and format single images.
|
||||
* Work with Options Panel or Shortcodes.
|
||||
|
||||
= NextGEN WordPress Gallery Plugin Community & Extensions =
|
||||
|
||||
NextGEN has been the dominant WordPress gallery plugin for years. As a result, there is large and great community of users and developers, as well as a large number of dedicated extension plugins. For a list of extension plugins, just search for NextGEN in the WordPress.org plugin repository, or visit our <a href="http://www.nextgen-gallery.com/nextgen-gallery-extension-plugins/">Complete List of NextGEN Extension Plugins</a>.
|
||||
|
||||
= NextGEN WordPress Gallery Plugin Resources =
|
||||
|
||||
*Visit the NextGEN <a href="http://www.nextgen-gallery.com" target="_blank">WordPress Gallery Plugin</a> official homepage<br>
|
||||
*Visit the <a href="http://www.nextgen-gallery.com/nextgen-pro" target="_blank">NextGEN Pro official landing page</a><br>
|
||||
*See <a href="http://www.nextgen-gallery.com/help/" target="_blank">NextGEN Gallery Documentation</a><br>
|
||||
*Get <a href="http://wordpress.org/tags/nextgen-gallery?forum_id=10" target="_blank">NextGEN Support</a> via the WordPress.org forums<br>
|
||||
*Get <a href="http://www.nextgen-gallery.com/languages/" target="_blank">Translations</a> for your own language<br>
|
||||
*See <a href="http://www.photocrati.com/photography-wordpress-themes" target="_blank">WordPress Photography Themes</a> by the same author<br>
|
||||
*Follow NextGEN Gallery on <a title="Follow NextGEN Gallery on Facebook" href="http://www.facebook.com/NextGENGallery" target="_blank">Facebook</a>, <a title="Follow NextGEN Gallery on Twitter" href="http://twitter.com/NextGENGallery" target="_blank">Twitter</a>, and <a title="Follow NextGEN Gallery on Google +" href="http://plus.google.com/101643895780935290171" target="_blank">Google +</a><br>
|
||||
|
||||
|
||||
== Credits ==
|
||||
|
||||
Copyright:<br>
|
||||
Photocrati Media 2012-2013<br>
|
||||
Alex Rabe 2007-2011
|
||||
|
||||
This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
** Please note **
|
||||
|
||||
NextGEN Gallery's flash slideshow option is powered by the JW Image Rotator from Long Tail Video. The Image Rotator is provided free as part of our plugin package thanks to a special arrangement with Long Tail Video. Over time, we will be moving away from reliance on this file. For more information, see the Long Tail Video website: http://www.longtailvideo.com.
|
||||
|
||||
== Installation ==
|
||||
|
||||
INSTALLATION: The easiest way to enjoy NextGEN Gallery is to login to you WordPress dashboard, go to Plugins >> Add New, search for NextGEN Gallery, and click to install. You can also download the zip file from this page and upload it from the Plugins >> Add New > Upload page.
|
||||
|
||||
HOW TO USE: Just go to a page or post and click the NextGEN Gallery icon. From our Attach to Post interface, you can create, manage, customize, and display your galleries. You can also manage your galleries and gallery settings from the central options area under the "Gallery" tab on your dashboard menu.
|
||||
|
||||
DOCUMENTATION: See <a href="http://www.nextgen-gallery.com/help/" target="_blank">NextGEN Gallery Documentation</a>.
|
||||
|
||||
That's it ... have fun! For more information, feel free to visit the official website for the NextGEN Gallery <a href="http://www.nextgen-gallery.com" target="_blank">WordPress Gallery Plugin</a>.
|
||||
|
||||
http://www.youtube.com/watch?v=Le_ZsNSuIvM
|
||||
|
||||
== Screenshots ==
|
||||
|
||||
1. NextGEN Thumbnail Gallery
|
||||
2. NextGEN Slideshow Gallery
|
||||
3. NextGEN Imagebrowser Gallery
|
||||
4. NextGEN Central Gallery Settings Page
|
||||
5. NextGEN Other Options Page - Watermarking
|
||||
6. NextGEN Manage Gallery Page - Edit Thumbnails
|
||||
7. NextGEN Manage Gallery Page - Edit Image Tags
|
||||
8. NextGEN Interface for Adding Galleries to a Page or Post
|
||||
9. NextGEN NextGEN Placeholder Image When Editing a Page or Post
|
||||
|
||||
== Shortcode ==
|
||||
|
||||
NextGEN Gallery 2.0 introduces our new Attach to Post interface, which means you never need to work with shortcodes again if you would prefer not too.
|
||||
|
||||
If you do want to work with shortcodes, we've also introduce a new, more powerful, and more flexible shortcode system with NextGEN Gallery 2.0.
|
||||
|
||||
**<a href="http://www.nextgen-gallery.com/nextgen-gallery-shortcodes">Learn About NextGEN Gallery 2.0 Shortcodes</a>**
|
||||
|
||||
Legacy shortcodes? For reference, we're also maintaining documentation on NextGEN Legacy shortcodes used in NextGEN 1.9.x and earlier. <a href="http://www.nextgen-gallery.com/shortcodes">See more on Legacy shortcodes</a>.
|
||||
|
||||
For more information, feel free to visit the official website for the NextGEN Gallery <a href="http://www.nextgen-gallery.com" target="_blank">WordPress Gallery Plugin</a>.
|
||||
|
||||
== Frequently Asked Questions ==
|
||||
|
||||
|
||||
= Why are my galleries not opening up in a lightbox after I move my site? =
|
||||
|
||||
This is often due to the URL paths to the CSS and JavaScript files used by the Lightbox Effects not being changed to relevant addresses based on the new site. This article will help sort out this issue if that is the case: <a href="http://www.nextgen-gallery.com/galleries-opening-lightbox/" target="_blank">Why are my galleries not opening up in a lightbox?</a>.
|
||||
|
||||
= Do you have documentation or tutorials? =
|
||||
|
||||
Yes. See <a href="http://www.nextgen-gallery.com/help/" target="_blank">NextGEN Gallery Documentation</a>.
|
||||
|
||||
= Will NextGEN Gallery work with my theme? =
|
||||
|
||||
Part of what makes the NextGEN Gallery WordPress gallery plugin so popular is its flexibility - it works with the vast majority of premium and free themes, without requiring any coding.
|
||||
|
||||
|
||||
= Are the galleries flash based? =
|
||||
|
||||
No, NextGEN Gallery uses Javascript (J-Query) based displays to ensure compatibility across the widest range of displays possible.
|
||||
|
||||
|
||||
= Are the galleries mobile friendly? =
|
||||
|
||||
Yes, since we use Javascript rather than flash, NextGEN Gallery is compatible with Android, iOS, and Blackberry. As of July 2013, all galleries are responsive. NextGEN Pro also includes a full screen, responsive Pro Lightbox with mobile gesture support.
|
||||
|
||||
|
||||
= What is the difference between a gallery and an album? =
|
||||
|
||||
In the simplest of terms, Galleries contain your images and Albums contain your Galleries. Albums act as links and placeholders to quickly and easily navigate your galleries - Galleries will actually display your images.
|
||||
|
||||
|
||||
= Can I upload multiple images at once? =
|
||||
|
||||
Yes, you can batch upload entire galleries at a time.
|
||||
|
||||
|
||||
= Can I password protect galleries? =
|
||||
|
||||
Yes, WordPress allows you to password protect pages by default - which includes all galleries and content for the entire page. Password protection of pages can be turned on and off at any time, with just a few clicks.
|
||||
|
||||
|
||||
= Can I add a watermark to the images/slideshows? =
|
||||
|
||||
Yes, you can add text or image watermarks to your gallery images.
|
||||
|
||||
|
||||
= Can I crop thumbnails? =
|
||||
|
||||
Yes, each thumbnail image can be individually adjusted to suit your needs.
|
||||
|
||||
|
||||
= Is there pagination for galleries? =
|
||||
|
||||
Yes, and you can adjust the amount of images to be shown on a page at any time.
|
||||
|
||||
|
||||
= Can I customize the lightbox? =
|
||||
|
||||
Yes, the lightbox can be configured with multiple options directly from the Dashboard, and there are multiple CSS styles which can be applied and modified as well.
|
||||
|
||||
|
||||
= Can I add HTML to the captions? =
|
||||
|
||||
Yes, caption areas are fully HMTL capable.
|
||||
|
||||
|
||||
= Can I add an external links to galleries? =
|
||||
|
||||
Since the captions are fully HTML capable, you can add external links and any other type of mark up you wish.
|
||||
|
||||
|
||||
= Is NextGEN Gallery available in foreign languages? =
|
||||
|
||||
Yes, the NextGEN Gallery WordPress gallery plugin has been translated into dozens of languages - <a href="http://www.nextgen-gallery.com/languages/" target="_blank">click here to find out more.</a>
|
||||
|
||||
|
||||
= More Information =
|
||||
|
||||
For more information, feel free to visit the official website for the NextGEN Gallery <a href="http://www.nextgen-gallery.com" target="_blank">WordPress Gallery Plugin</a>.
|
||||
|
||||
|
||||
== Changelog ==
|
||||
|
||||
= V2.0.66.33 - 11.24.2014 =
|
||||
* Fixed: Broken NextGEN Pro ecommerce-related shortcodes
|
||||
* Fixed: Spanish PO file
|
||||
|
||||
= V2.0.66.31 - 11.21.2014 =
|
||||
* Fixed: Broken shortcodes with WordPress 4.0.1
|
||||
|
||||
= V2.0.66.29 - 09.17.2014 =
|
||||
* NEW: Added skip_excluding_globally_excluded_images property to displayed gallery objects
|
||||
* Fixed: SQL generation for random image selection
|
||||
* Fixed: Adjust regex for replacing displayed gallery placeholder images
|
||||
* Fixed: Removed filters to home_url needed previously for WMPL compatibility
|
||||
* Fixed: Use canonical redirects when appropriate
|
||||
* Fixed: Ability to override image files using XML-RPC
|
||||
|
||||
= V2.0.66.27 - 08.18.2014 =
|
||||
* Fixed: Missing class.frame_communication_option_handerl.php error
|
||||
|
||||
= V2.0.66.26 - 08.18.2014 =
|
||||
* NEW: Added fault tolerance to bulk action AJAX requests
|
||||
* Changed: Moved some settings from DB to in-memory
|
||||
* Fixed: Compatibility with BuddyPress plugin in multisite environments
|
||||
* Fixed: Ability to find static resources outside of WP_PLUGIN_DIR
|
||||
* Fixed: Autoupdate conflict with Photocrati Theme
|
||||
* Fixed: Workaround GoDaddy's throttling of consecutive AJAX requests
|
||||
* Fixed: Issue with settings manager in multisite enviroments
|
||||
|
||||
= V2.0.66.17 - 08.08.2014 =
|
||||
* NEW: Added french translations
|
||||
* Secured: XSS vulnerability in jQuery Plupload Queue (thanks Codevigilant Team)
|
||||
* Secured: XSS vulnerability in thumbnail/slideshow integration links
|
||||
* Secured: XSS vulnerability on Manage Albums page
|
||||
|
||||
= V2.0.66.16 - 07.30.2014 =
|
||||
* NEW: Added new "limit" setting to Slideshow widgets
|
||||
* NEW: Added a "ngg_routes" action for other plugins to hook into to provide new routes
|
||||
* NEW: Added NGG_SKIP_LOAD_SCRIPTS constant, which existed in 1.9.x
|
||||
* NEW: Added NGG_GALLERY_ROOT_TYPE constant. Set to 'content' to load galleries from the content_dir / content_url
|
||||
* NEW: Bosnian (bs_BA) language thanks to Nevesin Srdoc
|
||||
* NEW: Chinese (zh_CN) language thanks to Vahi Chen, http://www.vahichen.com
|
||||
* NEW: Dutch (nl_NL) language thanks to Taeke Kooiker
|
||||
* NEW: Filipino (fil) language thanks to Find Hold, http://www.findhold.dk/
|
||||
* NEW: French (fr_FR) language thanks to Jean-Yves Dumaine & Le Blog de Lise
|
||||
* NEW: Hungarian (hu_HU) language thanks to Zoltán Varanka
|
||||
* NEW: Italian (it_IT) language thanks to Jacopo Caggiano, @tizz
|
||||
* NEW: Russian (ru_RU) language thanks to SnakeD3
|
||||
* NEW: Spanish (es_ES) language thanks to Andrew Kurtis at WebHostingHub
|
||||
* Changed: Updated Czech language thanks to Separatista; additional thanks to Martin Krizek for the original translation who was mistakenly unaccredited
|
||||
* Changed: "Upgrade to Pro" page has new design, advertises for NextGEN Plus
|
||||
* Changed: Basic Albums templates now given the image counter P element the class 'ngg-album-gallery-image-counter' (by user request)
|
||||
* Changed: Gallery widgets now apply height:auto to their element; fixes compatibility with some themes
|
||||
* Changed: Random galleries should be substantially faster now (1000% or more for large image tables)
|
||||
* Fixed: Complete WPML compatibility
|
||||
* Fixed: Disable Buddypress 'bp_do_redirect_canonical' filter as it ruins our routing system
|
||||
* Fixed: Use plugins_url() content_url() when appropriate rather than just site_url() and home_url()
|
||||
* Fixed: WP Cron job will remove not only displayed gallery transients, but rendering transients as well
|
||||
* Fixed: NGG_RENDERING_CACHE_TTL constant is honored properly
|
||||
* Fixed: If using the caption template for Basic Thumbnails, only show the image caption when appropriate
|
||||
* Fixed: If NGG is uninstalled, so are it's custom capabilities
|
||||
* Fixed: Translate "Attach NextGEN Gallery to Post" ATP icon alt text when translations are active
|
||||
* Fixed: Multisite gallery path tooltip gave a wrong default setting
|
||||
* Fixed: Flush 'all' caches when pope_module_list setting changes
|
||||
* Fixed: Don't enqueue related images css in the admin
|
||||
* Fixed: Basic Slideshows fixes WP creating extraneous P element above the slideshow display
|
||||
* Fixed: Basic Singlepic will now display images marked 'excluded' in the admin
|
||||
* Fixed: Admin pages can now update when the "Save" button text has been translated
|
||||
|
||||
= V2.0.66 - 05.20.2014 =
|
||||
* Secured: Check mime type of image files using a variety of mechanisms
|
||||
|
||||
= V2.0.65 - 05.04.2014 =
|
||||
* Secured: Limit uploads to images and zips
|
||||
|
||||
= V2.0.63 - 04.29.2014 =
|
||||
* NEW: Translation ready
|
||||
* NEW: Including German translation by Roland Stumpp
|
||||
* NEW: Including Czech translation by Separatista
|
||||
* NEW: Including Finnish translation by Vesa Tiirikainen
|
||||
* NEW: WPML / qTranslate support
|
||||
* NEW: Bundled Browser+ JavaScript library
|
||||
* NEW: Added NGG_DISABLE_FILTER_THE_CONTENT constant to manage conflicts
|
||||
* Changed: Moved jquery.nextgen_radio_toggle.js to NextGEN Admin Module
|
||||
* Changed: Original display settings are passed to secondary display types
|
||||
* Fixed: Thumbnail dimension calculations are inaccurate by 1px when maintaining aspect ratio
|
||||
* Fixed: Copy IPTC data from original to new image when creating new sizes / thumbnails
|
||||
* Fixed: Use correct absolute path when importing images in a multisite environment
|
||||
* Fixed: Incorrect display of disk space quotas in multisite environments
|
||||
* Fixed: Removed redundant roles form in multisite environments
|
||||
* Fixed: Insert Gallery Window support for multisite environments
|
||||
* Fixed: Incorrect handling of NextGEN Styles in multisite environments
|
||||
* Fixed: Not honouring NGG_IMPORT_ROOT constant
|
||||
* Fixed: Fixed inability to edit gallery properties using XMLRPC's edit_gallery method
|
||||
* Fixed: Alignment issues in Basic Compact Albums caused by subalbums not displaying image 'counter'
|
||||
* Fixed: Display setting forms compatibility issue with WordPress 3.9
|
||||
* Fixed; Compability with jQuery Dialogs in WordPress 3.9
|
||||
* Fixed: Maximum entity code should be a displayed gallery property for recent/random sources only
|
||||
* Fixed: Problems with zlib compression: https://core.trac.wordpress.org/ticket/18525
|
||||
* Fixed: Support for web servers which use a document root of '//'
|
||||
* Fixed: Compatibility with WPML Translation Management
|
||||
* Fixed: use 'del' for function name in ngg_store.js, 'delete' is a reserved keyword
|
||||
* Fixed: Enqueue fontawesome only when necessary
|
||||
* Fixed: Suhosin compatibility issue when overriding PHP memory limit
|
||||
* Fixed: Handle images of wrong image type correctly when trying to create cropped thumbnails
|
||||
* Fixed: Datamapper entities not allowed to have properties with a value of 0
|
||||
* Fixed: Resource manager is manipulating feeds
|
||||
* Fixed: Convert absolute urls to relative urls for lightboxes
|
||||
* Fixed: Start the resource manager as early as we can within the init action
|
||||
* Fixed: Routing problem for galleries with images named 1.jpg, 2.jpg, 3.jpg, etc.
|
||||
* Fixed: Added tooltips to basic slideshow settings
|
||||
* Fixed: Remove CKEditor's NextGEN button, which is incompatible with NextGEN Gallery 2.x
|
||||
|
||||
= V2.0.61 - 04.01.2014 =
|
||||
* Fixed: Compatibility with WP 3.9
|
||||
* Fixed: Exception thrown when using Reset button
|
||||
|
||||
= V2.0.59 - 03.18.2014 =
|
||||
* Changed: Separated pope_module_list from ngg_options record in options table
|
||||
* Fixed: Removed code causing jQuery compatibility issues in WP Admin
|
||||
* Fixed: Allow third-parties to override jQuery with Google's CDN
|
||||
* Fixed: When resetting the 'jquery' handle, ensure that jquery-migrate is a dependency
|
||||
* Fixed: Silenced many PHP warnings
|
||||
* Fixed: Datamapper->count() not returning the correct count
|
||||
* Fixed: Compatibility with Gravity Forms
|
||||
|
||||
= V2.0.58 - 03.09.2014 =
|
||||
* Fixed: Reset jQuery to WP defaults when modified by a third-party
|
||||
* Fixed: Compatibility with WP jQuery Lightbox plugin
|
||||
* Fixed: Compatibility with Peekaboo theme
|
||||
|
||||
= V2.0.57 - 03.05.2014 =
|
||||
* NEW: Re-introduced the Reset button
|
||||
* NEW: Tooltip added for Page Link to functionality
|
||||
* NEW: Displayed Gallery Triggers moved from NextGEN Pro to NextGEN Gallery (not in use)
|
||||
* NEW: Added NGG_Store, a client-side persistence layer (not in use)
|
||||
* NEW: Added NGG_CRON_SCHEDULE constant. Set to the number of seconds between the execution of NextGEN Gallery cron jobs
|
||||
* NEW: Added NGG_RENDERING_CACHE_TTL constant. TTL measured in seconds.
|
||||
* NEW: Added NGG_DISPLAYED_GALLERY_CACHE_TTL constant. TTL measured in seconds.
|
||||
* NEW: Added NGG_DISABLE_LEGACY_SHORTCODES constant. When TRUE, [slideshow] becomes [nggslideshow].
|
||||
* NEW: Added Font Awesome, available for NextGEN Gallery extensions
|
||||
* Changed: Transients are removed every 30 minutes instead of 60 minutes
|
||||
* Changed: Admin Page & Form components refactored to allow custom POST processing
|
||||
* Changed: Default path for NEW multisite installations to wp-content/uploads/sites/%BLOG_ID%/nggallery/
|
||||
* Fixed: Ability to upload ZIP files on Windows hosts
|
||||
* Fixed: Support for filenames with non-ASCII characters
|
||||
* Fixed: Dynamic updates in the Attach to Post interface (interframe communication)
|
||||
* Fixed: Attach to Post interface freezing in IE11
|
||||
* Fixed: Path issues on Windows Servers
|
||||
* Fixed: Module installer integrity
|
||||
* Fixed: Database query performance. No more joins to the WP options table
|
||||
* Fixed: Lightboxes storing absolute paths for static resources
|
||||
* Fixed: Displayed gallery cache not regularly flushed
|
||||
* Fixed: SQL query performance problems. Honor max_packet_allowed variable for MySQL
|
||||
* Fixed: Multiple database queries generated for determining next available image slug
|
||||
* Fixed: Corrupted MediaRSS feeds
|
||||
* Fixed: Padding on Gallery Settings and Other Options pages
|
||||
* Fixed: Routing issues on subdirectory installs
|
||||
* Fixed: Importing galleries using the Attach to Post Interface
|
||||
* Fixed: Gallery path calculations on Windows web servers
|
||||
* Fixed: Sub-album urls not processed correctly
|
||||
* Fixed: Apply maximum entity count to existing displayed galleries
|
||||
* Fixed: NextGEN Gallery Thumbnail Widget shouldn't use ImageBrowser effect
|
||||
* Fixed: Ability to set shuffle parameter for ImageRotator slideshows
|
||||
* Fixed: PHP warning about HTMLDocument when displaying a SinglePic
|
||||
* Fixed: Sanitization of gallery title
|
||||
* Fixed: Home URL now used instead of Site URL in MediaRSS feed
|
||||
* Fixed: Attach to Post interface broken when WPML is installed
|
||||
* Fixed: Attach to Post interface instructing browser to cache the page
|
||||
* Fixed: Watermarking not working in low-memory environments
|
||||
* Fixed: Maximum images limit not being applied for galleries already created.
|
||||
* Fixed: Double forward slashes in static urls
|
||||
* Fixed: Don't sleep when checking if the installer is running
|
||||
* Fixed: Don't enforce Pope interface contracts
|
||||
* Fixed: Remove custom table extra records from wp_options table
|
||||
* Fixed: Scan folder for new images not working
|
||||
* Fixed: Incorrect page permalink used for "Page Link To" functionality
|
||||
* Fixed: Pagination broken when Basic Thumbnail gallery on the same page as Basic Album
|
||||
* Fixed: parse_url() warnings generated for PHP 5.3.3 and earlier
|
||||
* Fixed: Compatibility with Headway Themes
|
||||
* Fixed: Compatibility with web servers which don't provide PHP a document root
|
||||
* Fixed: Third-party incompatibilities caused by the Photocrati Resource Manager
|
||||
* Fixed: Compatibility with the Flattr plugin
|
||||
* Fixed: Compatibility with the Weaver II theme
|
||||
* Fixed: Interface tweaks for WordPress 3.8
|
||||
|
||||
= V2.0.40 - 11.26.2013 =
|
||||
* NEW: Added the ability to apply lightbox effects to non-NGG images
|
||||
* NEW: Added NGG_HIDE_STRICT_ERRORS constant. Define and set to TRUE to hide strict errors
|
||||
* NEW: Added NGG_IMPORT_ROOT constant. Define and set to TRUE to browse from a custom directory
|
||||
* NEW: Added NGG_DEBUG constant. Define and set to TRUE to display helpful messages for debugging
|
||||
* NEW: Each custom table record will have an associated custom post record for expansion
|
||||
* NEW: Display helpful error messages when there's a problem uploading images
|
||||
* NEW: Add data-(src|thumbnail|image-id|title|description) attribute to gallery image anchors
|
||||
* NEW: Variant support for displayed gallery sources. Random images is limited to 5 variations
|
||||
* Fixed: Excessive creation of transients for random galleries
|
||||
* Fixed: Many issues prohibiting the ability to upload images
|
||||
* Fixed: Compatibility with NextGEN Gallery Export Plugin for Adobe Lightroom (thanks Vladimir!)
|
||||
* Fixed: Sorting in the Attach to Post interface
|
||||
* Fixed: HTML allowed in gallery/album descriptions
|
||||
* Fixed: Requests for galleries within albums that have numeric names are broken
|
||||
* Fixed: Call to a non-member function get() on WP_Query
|
||||
* Fixed: Ability to sort by Image ID in the Attach to Post interface
|
||||
* Fixed: Isolate the Attach to Post from implicit third-party script inclusion
|
||||
* Fixed: Check for the existance of thumbnails when generating urls, and if missing, generate new ones
|
||||
* Fixed: Compatibility with NextGEN Facebook OpenGraph+ plugin
|
||||
* Fixed: Various XML-RPC issues
|
||||
* Fixed: Widgets stylesheet not included
|
||||
* Fixed: Issue with color not being pre-selected when previewing Watermark
|
||||
* Fixed: E_NOTICE emitted when cleaning up cached image files
|
||||
* Fixed: E_NOTICE emitted when viewing display type settings
|
||||
* Fixed: Typo adjusting pcre.backtrack_limit for shortcodes
|
||||
* Fixed: Content within the tabs of the Attach to Post interface cut-off
|
||||
* Fixed: Routing problem which would cause conflicts with different display types on the same page
|
||||
* Fixed: Broken Dynamic CSS links on GoDaddy
|
||||
* Fixed: Ability to use HTML in gallery/album descriptions
|
||||
* Fixed: Sub-album requests conflicting with paginated galleries on the same page
|
||||
* Merged: Pull request from andreasE (https://bitbucket.org/photocrati/nextgen-gallery/pull-request/6/)
|
||||
|
||||
= V2.0.33 - 10.21.2013 =
|
||||
* NEW: Requests /ngg_tag/[tagname] will create a displayed gallery
|
||||
* NEW: Option added to "Import Gallery" tab to use original images
|
||||
* Fixed: Links are broken on the ngg_tags-sitemap.xml file by WordPress SEO
|
||||
* Fixed: PHP notice: Attempt to assign property of non-object
|
||||
* Fixed: Undefined property warnings when using NextGEN Basic Thumbnails
|
||||
* Fixed: Detect if an applying a transient to a displayed gallery was successful
|
||||
* Fixed: Compatibility issues with BJ-Lazy-Load and Colorbox
|
||||
* Fixed: Pagination conflicts for multiple Imagebrowsers on the same page
|
||||
* Fixed: Ability to display previous exception with debug mode
|
||||
* Fixed: Tagclouds not working in multisite instances
|
||||
* Fixed: Load widgets.css when a widget is being used
|
||||
* Fixed: Installer should remove all instances of the component factory
|
||||
* Fixed: Widget settings interface not intuitive
|
||||
* Fixed: Inability to upload images in some Windows host environments
|
||||
* Fixed: Sorting images/galleries using the Attach To Post interface
|
||||
* Fixed: Fix detection of HTTPS (pull request by Leonhardt Wille)
|
||||
* Fixed: Compilation errors of regular expressions
|
||||
* Fixed: Pro galleries wouldn't display in environments using PHP 5.3.3 or less
|
||||
* Fixed: Scanning of router slug is now limited to the uri, not the url
|
||||
* Fixed: Show slideshow link isn't required for thumbnail/imagebrowser integration
|
||||
* Fixed: WordPress media-upload with 'singlepic' image size
|
||||
* Fixed: Use target=_blank when the link setting is provided for NextGEN Basic Singlepic
|
||||
* Fixed: Only display rendering errors if WP_DEBUG is enabled
|
||||
|
||||
= V2.0.31 - 10.03.2013 =
|
||||
* NEW: Restored AJAX pagination for NextGEN Basic ImageBrowser display type
|
||||
* Fixed: Compatibility with WordPress Local SEO by Yoast
|
||||
* Fixed: Inability to upload images if image_slug field was missing in database
|
||||
* Fixed: Integration of NextGEN Basic Thumbnail and NextGEN Basic Slideshow display types
|
||||
* Fixed: Photocrati Resource Manager further adjusted to be third-party friendly
|
||||
* Fixed: Added the ability to find legacy templates in both the child/parent theme directories
|
||||
* Fixed: JavaScript errors in Attach to Post interface
|
||||
* Fixed: Router can handle port numbers in urls
|
||||
* Fixed: Carousel template was linking to NextGEN Basic ImageBrowser view
|
||||
* Fixed: SQL query generated for displayed galleries using tags as source
|
||||
* Fixed: 3rd party compat: raise & never lower pcre.backtrack_limit
|
||||
|
||||
= V2.0.30 - 09.25.2013 =
|
||||
* NEW: Restored the ability to use imagebrowser display type instead of a lightbox effect
|
||||
* Changed: Displayed galleries are no longer rendered in RSS feeds
|
||||
* Changed: Removed "Plugin Check" widget from overview page
|
||||
* Fixed: Silence PHP warnings/errors in an output buffer for AJAX actions
|
||||
* Fixed: Compatibility issue with WordPress SEO and broken site maps (and large error_logs)
|
||||
* Fixed: Compatibility issue with AJAX Event Calendar (and possibly others)
|
||||
* Fixed: Adjusted Photocrati Resource Manager to be third-party friendly
|
||||
* Fixed: Fixed empty result set for displayed galleries selecting 'All' tags
|
||||
* Fixed: URL generation for imagebrowser pagination links
|
||||
* Fixed: Ensure that image meta is imported on creation
|
||||
* Fixed: Ensure that transients are removed when an external object cache is used
|
||||
* Fixed: Don't load pluggable.php. This will fix plugin conflicts
|
||||
* Fixed: In Attach to Post interface, galleries created in one tab weren't showing in another
|
||||
* Fixed: Don't output frame events cookie for XML-RPC requests
|
||||
|
||||
= V2.0.27 - 09.18.2013 =
|
||||
* Fixed: Reduce performance impact of purging displayed gallery transients
|
||||
|
||||
= V2.0.25 - 09.18.2013 =
|
||||
* Reverting to the 2.0.21 codebase, due to major performance issues in 2.0.23 and 2.0.24
|
||||
|
||||
= V2.0.23 - 09.16.2013 =
|
||||
* NEW: WP-Cron job to periodically clean-up displayed gallery transients
|
||||
* NEW: Added "excluded_container_ids" as parameter for ngg_images shortcode
|
||||
* Fixed: Lightbox effect is honoured by all display types
|
||||
* Fixed: Highslide displays images from the correct displayed galleries
|
||||
* Fixed: Ensure that sub-albums display correctly when the word "album" is part of a slug
|
||||
* Fixed: Ensure that sub-albums display correctly when numerical slugs are used
|
||||
* Fixed: Related images heading only added when Related Images functionality is enabled
|
||||
* Fixed: PHP Warning about undefined index when viewing basic albums
|
||||
* Fixed: AJAX handling is third-party compatible
|
||||
* Fixed: Image date is no longer overwritten when an image is modified
|
||||
* Fixed: Fixed issue with displayed galleries using source='tags'
|
||||
* Fixed: Problem with transient cache not getting flushed properly from Other Options page
|
||||
* Fixed: Use correct gallery/transient ID when ajax pagination is used
|
||||
|
||||
= V2.0.21 - 09.09.2013 =
|
||||
* NEW: Multisite support
|
||||
* Changed: Default image quality set to 100 for generated images
|
||||
* Changed: Removed dependence on simplehtmldom library
|
||||
* Fixed: Related images functionality works as it did in 1.9.x
|
||||
* Fixed: Don't compress inline JavaScript in post/page content
|
||||
* Fixed: Click-to-advance slideshow behavior for slideshows
|
||||
* Fixed: Security warnings from VaultPress
|
||||
* Fixed: View as Slideshow link works with AJAX pagination
|
||||
* Fixed: Broken links on Overview page
|
||||
* Fixed: Backup images option
|
||||
* Fixed: Stylesheet url generated correctly for Windows hosts
|
||||
* Fixed: Compatibility with NextGen Custom Fields plugin
|
||||
* Fixed: Compatibility with Adsense Explosion plugin
|
||||
* Fixed: Suppress wp_footer notices unless WP_DEBUG is set to TRUE
|
||||
|
||||
= V2.0.17 - 08.30.2013 =
|
||||
Fixed: Match legacy behaviour when changing gallery path, i.e. don't move files
|
||||
|
||||
= V2.0.14 - 08.27.2013 =
|
||||
* NEW: Added the ability to override thumbnail settings for NextGEN Basic Albums
|
||||
* NEW: Shortcode Manager API, which ensures that shortcodes are outputted as intended
|
||||
* Changed: Re-added the ability to select the original image size for widgets
|
||||
* Fixed: Ensure that stylesheet url returned is correct for Windows hosts
|
||||
* Fixed: Broken links and lightbox effects with AJAX pagination
|
||||
* Fixed: Try to ensure that third party plugins don't add content to our dynamic JS
|
||||
* Fixed: Improved reliability of iframely.js
|
||||
* Fixed: Ensure that urls are generated correctly in HTTPs environments
|
||||
* Fixed: Datamapper works correctly in environments where temporary tables aren't supported
|
||||
* Fixed: Fixed an issue with thickbox loading animation when home url differs from site url
|
||||
|
||||
= V2.0.11 - 08.19.2013 =
|
||||
* NEW: Added "run_ngg_resource_manager" hook to by-pass our resource manager
|
||||
* Changed: Removed "Reset & Uninstall" tab, for now
|
||||
* Fixed: Compatibility with W3 Total Cache. Please flush cache after updating.
|
||||
* Fixed: Conflicts with Photocrati Theme Galleries
|
||||
* Fixed: Blank Attach to Post interface window
|
||||
* Fixed: Fixed ability to change Lightbox Effect settings
|
||||
* Fixed: Implemented techniques to ensure WP_Query variables aren't overwritten
|
||||
* Fixed: Enqueuing AJAX JS libraries twice in wp-admin
|
||||
* Fixed: Encoding issues
|
||||
* Fixed: PHP warnings caused by accessing unserialized data as array
|
||||
* Fixed: Fixed installer issues
|
||||
|
||||
= V2.0.7 - 08.09.2013 =
|
||||
* NEW: New resource manager that fixes many plugin and theme incompatibilities
|
||||
* NEW: Styles (custom stylesheets) should reside in wp-content/ngg_styles
|
||||
* NEW: Added option to "Other Options -> Misc" to control maximum images returned
|
||||
* Secured: Removed default connector for jQuery FileTree library
|
||||
* Changed: Updated the simplehtmldom library to version 1.5
|
||||
* Changed: jQuery is now enqueued at the beginning of every request
|
||||
* Fixed: Incompatibilities with BuddyPress
|
||||
* Fixed: Incompatibilities with Events+, bbPress, Custom Permalinks, and many other plugins
|
||||
* Fixed: Incompcatibilities with Member Access, AMember, Magic Fields, and More Fields
|
||||
* Fixed: Incompatibilities with Elegant Themes, Oxygen, Responsive, and many other themes
|
||||
* Fixed: Ensure that gallery images don't have a border by default
|
||||
* Fixed: Conflict between imagebrowser and album urls
|
||||
* Fixed: Reverted default gallerypath to wp-content/gallery/
|
||||
* Fixed: Upgrade-safe way of overriding Styles
|
||||
* Fixed: Generation of AJAX url is now based on slug
|
||||
* Fixed: Restore nggShowGallery and nggShowSlideshow as wrappers to new API
|
||||
* Fixed: Always use domain as specified by WordPress Site URL
|
||||
* Fixed: Use WordPress Home URL over Site URL when appropriate
|
||||
* Fixed: Numerous pagination issues
|
||||
* Fixed: Adjusted our forms to comply with WordPress Firewalls
|
||||
* Fixed: Correct use of select2 DOM selector for maximum compatibility
|
||||
* Fixed: Path and URL calculations for Windows and UNIX environments
|
||||
* Fixed: Ensure that pluggable.php is loaded at the start of every request
|
||||
* Fixed: Fancybox: adjust CSS for further box-sizing protection from themes
|
||||
* Fixed: Use PHP 5.2.1 compatible named pattern matching syntax
|
||||
* Fixed: Remove usage of __DIR__ constant not supported by PHP 5.2.x
|
||||
* Fixed: Removed dependency on mb_string PHP module
|
||||
* Fixed: Allow "No Lightbox" as an option for Lightbox Effects
|
||||
* Fixed: Warning: "Invalid CRT parameters detected" for Windows environments
|
||||
|
||||
= V2.0 - 07.30.2013 =
|
||||
* NEW: Improved user experience throughout the plugin, settings and usage.
|
||||
* NEW: Plupload queue uploader that allows for bulk and zip uploads within the same interface.
|
||||
* NEW: Complete redesign of the NextGEN options panel
|
||||
* NEW: Added new interface for adding galleries from pages and posts.
|
||||
* NEW: Galleries are now mobile friendly and responsive, which is most noticeable with a responsive theme.
|
||||
* NEW: Streamlined functionality for displaying galleries based on tags.
|
||||
* NEW: Architecture based on Pope Framework (http://bitbucket.org/photocrati/pope-framework)
|
||||
* NEW: New shortcode, “ngg_imagesâ€, and corresponding Attach to Post interface
|
||||
* NEW: Galleries have now global and instance settings
|
||||
* NEW: Support for FastCGI environments
|
||||
* Changed: Replaces shortcodes with placeholder images, however still supports legacy shortcodes.
|
||||
* Changed: Introduced new Growl-like notifications
|
||||
* Changed: The container and it’s images are centered for slideshows
|
||||
* Changed: NextGEN styles now override vs replace default styles
|
||||
* Changed: NextGEN legacy templates have been deprecated (but still function)
|
||||
* FIXED: The ability to use NextGEN image as a Featured Image.
|
||||
* FIXED: Many bugs and annoyances, such as PHP warnings, errors, etc.
|
||||
|
||||
= V1.9.13 - 06.11.2013 =
|
||||
* NEW: Slideshows are now centered to their content area
|
||||
* Secured: Ensure that only logged in users can upload images
|
||||
* Fixed: Import date is presered are no longer Jan 1 1970
|
||||
* Fixed: Removed mention of upgrade.php, which no longer exists
|
||||
|
||||
= V1.9.12 - 02.15.2013 =
|
||||
* Fixed: jQuery Conflict Detection was trying to dequeue irremovable scripts
|
||||
|
||||
= V1.9.11 - 02.12.2013 =
|
||||
* NEW: Added the ability to detect JQuery conflicts on NGG Admin Pages and auto-resolve
|
||||
* Changed: Added "nggalbum" shortcode. Use this when Jetpack is installed.
|
||||
* Changed: Using natural sorting algorithm for alphanumeric values
|
||||
* Changed: Database schema is automatically updated when out-of-date
|
||||
* Fixed: Fixed several incompatibility issues with Jetpack
|
||||
* Fixed: Empty drop-down for "Page Link To"
|
||||
* Fixed: Alphabetical image sorting
|
||||
* Fixed: Compatibility with Arjuna X theme
|
||||
* Fixed: “Creating default object from empty value†on album page
|
||||
* Fixed: Compatibility issues with PHP 5.4 on album page
|
||||
* Fixed: E_DEPRECATED warning when using get_userdatabylogin() function
|
||||
* Fixed: Removed many E_NOTICE errors
|
||||
* Fixed: Correct use of register_uninstall_hook across all PHP versions
|
||||
|
||||
= V1.9.10 - 12.18.2012 =
|
||||
* Fixed: XML-RPC error displayed when authenticating using WordPress 3.5
|
||||
* Fixed: Restored compatibility with NextGEN Gallery Export Plugin
|
||||
* Fixed: Removed some remaining references to database upgrade code
|
||||
* Fixed: Deleted galleries within an album are handed gracefully without warning messages
|
||||
* Fixed: Correct use of register_uninstall_hook
|
||||
* Fixed: CSS and usability issues with the TinyMCE window used to display galleries
|
||||
|
||||
* NEW: JW ImageRotator v3.17 is now bundled with the plugin and used by default.
|
||||
* Changed: Removed database upgrade code for versions of NextGEN Gallery earlier than 1.9.3
|
||||
* Fixed: Compatibility with WordPress v3.5 ( wpdb->prepare() warnings )
|
||||
* Fixed: Sorting by filename now produces expected results using a natural sorting algorithm
|
||||
|
||||
= V1.9.8 - 12.05.2012 =
|
||||
* Secured: Removed bundled version of swfupload. See fix below for SCM information.
|
||||
* Changed: All transients created by NextGEN are flushed when the plugin is activated.
|
||||
* Fixed: Our primary SCM is conducted at http://bitbucket.org/photocrati/nextgen-gallery, but was not synchronizing correctly with the WordPress Plugin SVN Repository
|
||||
* Fixed: The transient adjustment fixes: http://wordpress.org/support/topic/plugin-nextgen-gallery-_transient_ngg_request-entry-in-wp_options
|
||||
|
||||
= V1.9.7 - 11.13.2012 =
|
||||
* Secured: Removed bundled version of swfupload; using WordPress-bundled version instead for WordPress 3.2 instances
|
||||
* Changed: Using JQuery UI for the image sorting interface (thanks Tomás Soler)
|
||||
* Bugfix: Image uploads work in WP 3.2 when using Safari
|
||||
* Bugfix: Adjusted TinyMCE window to use built-in JavaScript libraries
|
||||
* Bugfix: Removed Photocrati acquisition announcement
|
||||
* Bugfix: Fixed incorrect usage of ImageJpeg() function
|
||||
* Bugfix: Switched from "template_redirect" to "wp_enqueue_script" hook to load scripts and styles
|
||||
|
||||
= V1.9.6 - 07.21.2012 =
|
||||
* Changed: Implemented workaround for bug found in WordPress SEO, resulting in no images being added to sitemap
|
||||
* Bugfix: Fixed an issue with users not being able to dismiss the "Photocrati Acquisition Notice"
|
||||
* Bugfix: Adjusted Javascript for activating social media pages to load on NextGEN Gallery pages only.
|
||||
* Bugfix: Fixed compatibility issue with Simple Facebook Connect
|
||||
* Bugfix: Using correct Facebook Page ID in Like button
|
||||
|
||||
= V1.9.5 - 18.07.2012 =
|
||||
* Changed: Branding changes following Photocrati acquisition (removed donation messages and updated links)
|
||||
* Secured: Use WordPress-bundled JavaScript libraries for swfobject and swfupload instead of bundling our own
|
||||
* Bugfix: Adjusted thickbox effect styling to ensure that the lightbox is always displayed in the foreground
|
||||
* Bugfix: Fixed compatibility issues with Contact Form 7 and other plugins by following WordPress Plugin conventions
|
||||
* Bugfix: Fixed network-wide activation in WordPress 3.4
|
||||
* Bugfix: Plugin is no longer dependent on it's folder name
|
||||
|
||||
= V1.9.3 - 26.02.2012 =
|
||||
* Bugfix : Ensure to set the slug for "all" albums
|
||||
* Bugfix : Updated german translation ( THX to Roger Hunziker )
|
||||
* Bugfix : Ensure error checking on IPTC array (THX to Kristian Edlund)
|
||||
* Bugfix : Handle IE8 cached images better in slideshow
|
||||
* Bugfix : Show album preview image if selected (THX to Kristian Edlund)
|
||||
|
||||
= V1.9.2 - 17.01.2012 =
|
||||
* NEW : Added more XMLRPC commands (THX to Vladimir Vinogradsky)
|
||||
* Changed : Rework Post-thumbnail function (THX to Kristian Edlund)
|
||||
* Bugfix : Check first for valid images on unzip (only Mac OS zip-files)
|
||||
* Bugfix : Increase z-index for twenty eleven theme
|
||||
* Bugfix : Support non latin chars in tagcloud
|
||||
* Bugfix : Allow other tinymce intance
|
||||
* Bugfix : Better support for WPML translation
|
||||
|
||||
= V1.9.1 - 10.12.2011 =
|
||||
* Bugfix : Security hardness for untrusted filenames/meta data (THX to Brian St. Pierre)
|
||||
* Bugfix : Fixed security vulnerability (TXH to Jon Cave)
|
||||
* Bugfix : Load piclens script via other function
|
||||
* Bugfix : IE7 script fix for add gallery
|
||||
* Bugfix : IE7/IE8 width set correctly for edit album autocomplete field
|
||||
|
||||
= V1.9.0 - 27.11.2011 =
|
||||
* NEW : Keep images transparency for PNG and GIF format
|
||||
* NEW : Switch to Plupload, support now HTML5 Upload (only with WordPress 3.3)
|
||||
* NEW : Added client side resize feature (only with WordPress 3.3)
|
||||
* NEW : Support for gallery templates in album shortcodes [ album id=x template="name" gallery="templatename" ]
|
||||
* NEW : Added new hook ngg_delete_picture
|
||||
* Changed : Updated to jQuery Cycle Version 2.9995
|
||||
* Changed : Always cache the single pictures, remove option
|
||||
* Bugfix : Couldn't use bulk operation for search results
|
||||
* Bugfix : Bugfix for Edit thumbnails under IE 8 + 9
|
||||
* Bugfix : Allow empty altext in ngg.editImage
|
||||
* Bugfix : Various PHP notice fixes
|
||||
* Bugfix : Resize fix for Shutter effect and mobile Browser
|
||||
* Bugfix : FTP Import missing slug field into database
|
||||
* Bugfix : Check also EXIF field "DateTimeOriginal" for timestamp
|
||||
|
||||
= V1.8.4 - 26.10.2011 =
|
||||
* Bugfix : Fixed security vulnerability (TXH to Alain Schneider)
|
||||
|
||||
= V1.8.3 - 07.08.2011 =
|
||||
* Changed : Support for simple custom permalink structures (i.e. /%category%/%postname%/)
|
||||
* Bugfix : Sub-Albums in Albums didn't create the correct link
|
||||
* Bugfix : AJAX Pagination didn't work anymore
|
||||
* Bugfix : Adding index.php to home_url()
|
||||
* Bugfix : Preview picture lost on backend gallery page 2 or higher
|
||||
|
||||
= V1.8.2 - 12.07.2011 =
|
||||
* Bugfix : Set pagination variables for search result, otherwise update failed
|
||||
* Bugfix : Update failed for paged galleries since WordPress 3.2
|
||||
|
||||
= V1.8.1 - 18.06.2011 =
|
||||
* Bugfix : Special case for pagination, instead of showing page-1, we show the clean url
|
||||
* Bugfix : Various PHP notice fixes
|
||||
* Bugfix : Typo in rewrite rules
|
||||
* Bugfix : Flush rewrite rules during upgrade later
|
||||
|
||||
= V1.8.0 - 12.06.2011 =
|
||||
* NEW : Full rework of permalink url structure
|
||||
* NEW : Adding Google Sitemaps for Images (require WordPress SEO plugin by YOAST )
|
||||
* NEW : Support for WPML ( WordPress Multilingual Plugin )
|
||||
* NEW : Adding support for arrow key in shutter effect (THX to Flyvans)
|
||||
* NEW : Adding sort operation for galleries overview page
|
||||
* Changed : Updated pagination to new WP3.1 style
|
||||
* Bugfix : Create unique slug in a better way
|
||||
* Bugfix : Rework screen options filter for gallery and image table
|
||||
* Bugfix : Empty values in XMLRPC update calls are ignored
|
||||
* Bugfix : Create gallery failed when safe-mode on
|
||||
* Bugfix : Permalink didn't work in combination with album & imagebrowser
|
||||
|
||||
= V1.7.4 - 15.02.2011 =
|
||||
* Bugfix : Disallow direct call of ajax file to avoid path disclosure (THX to High-Tech Bridge SA)
|
||||
* Bugfix : Rework jQuery Cycle slideshow for IE compat reason (THX to Justin Dickenson)
|
||||
* Bugfix : Resize only larger images in slideshow
|
||||
* Bugfix : Improved image format detection in gd.thumbnail class (THX to Kupar.b)
|
||||
|
||||
= V1.7.3 - 20.01.2011 =
|
||||
* NEW : Introduce plugin health check for conflicts with other plugins/themes
|
||||
* NEW : Adding new XMLRPC method ngg.deleteImage
|
||||
* NEW : Adding new XMLRPC method ngg.editImage
|
||||
* Changed : Rework register script for autocomplete feature
|
||||
* Bugfix : Bugfix for Multisite setup and flash upload
|
||||
* Bugfix : WP3.1 compat issue, show site admin page only on Multisite installation
|
||||
|
||||
= V1.7.2 - 13.12.2010 =
|
||||
* Bugfix : Adding images to database require slug (NOT NULL)
|
||||
|
||||
= V1.7.1 - 13.12.2010 =
|
||||
* Changed : Disable upgrade for PHP4 user
|
||||
* Changed : Disable colorpicker for option page
|
||||
* Bugfix : Compat fix for upgrade
|
||||
|
||||
= V1.7.0 - 11.12.2010 =
|
||||
* NEW : Publish a new post direct from the gallery admin page
|
||||
* NEW : Added filter hook 'ngg_get_image_metadata' to add more exif/iptc information
|
||||
* NEW : Adding Autocomplete field to TinyMCE Popup and Album page
|
||||
* NEW : More methods for XMLRPC interface
|
||||
* Changed : New hooks for gallery table (THX to Alexander Schneider)
|
||||
* Changed : Introduce jQuery dialog as new UI element
|
||||
* Changed : Call TinyMCE window via admin-ajax
|
||||
* Bugfix : Better support for SSL blogs
|
||||
* Bugfix : Install/Upgrade failed when table prefix contain captial letters
|
||||
* Bugfix : Fix validation issues in Media-RSS
|
||||
* Bugfix : Empty tags in XMP Meta causes PHP error
|
||||
* Bugfix : Rework load mechanism for slideshow
|
||||
* Bugfix : Copy meta data when image is copied
|
||||
* Bugfix : Icon Support for Ozh' Admin Drop Down Menu
|
||||
* Bugfix : Use correct sort order in slideshow
|
||||
|
||||
= V1.6.2 - 19.09.2010 =
|
||||
* NEW : Added constant NGG_SKIP_LOAD_SCRIPTS to avoid script load
|
||||
* Bugfix : Load Tags library with core files
|
||||
* Bugfix : Slideshow script failed in IE7, load script now in header
|
||||
* Bugfix : Load slideshow widget always
|
||||
* Changed : New admin notice for database upgrade
|
||||
* Changed : Rework crop feature for featured images
|
||||
* Changed : Use site_url() instead get_option ('siteurl'), required for SSL support
|
||||
|
||||
= V1.6.1 - 08.09.2010 =
|
||||
* Bugfix : Script load of swfobject.js failed
|
||||
* Bugfix : Show sideshow also with 1 or 2 images
|
||||
* Bugfix : Rework null byte check in zip upload
|
||||
|
||||
= V1.6.0 - 07.09.2010 =
|
||||
* NEW : Wordpress 3.0 Network (Multi-Site) support
|
||||
* NEW : Integrate jQuery Cycle as NON-Flash slideshow
|
||||
* NEW : Adding jQuery File Tree for import folder (THX to Sergey Pasyuk )
|
||||
* NEW : Added action hook 'ngg_show_imagebrowser_first' on custom request
|
||||
* NEW : Added filter hook 'ngg_slideshow_size' to resize sildeshow for mobile browser plugins
|
||||
* Changed : Reorder tabs for upload
|
||||
* Changed : New menu icon and screen icon (THX to Ben Dunkle)
|
||||
* Changed : Load frontend libs always
|
||||
* Changed : Rework of overview page
|
||||
* Bugfix : Security bugfix for Zip-Upload (THX to Dominic Szablewski)
|
||||
* Bugfix : Allow JPG, PNG, GIF extension
|
||||
* Bugfix : New German translation (THX to Martin Kramarz)
|
||||
* Bugfix : Copy/Move also backup file
|
||||
* Bugfix : Calculate correct ratio for fix thumbnail size (THX to Alekz Keck)
|
||||
|
||||
= V1.5.5 - 14.06.2010 =
|
||||
* Bugfix : Compat issue for post thumbnails with WP2.9
|
||||
* NEW : Adding more hooks for custom fields plugin
|
||||
|
||||
= V1.5.4 - 14.06.2010 =
|
||||
* Bugfix : No resize of smaller images
|
||||
* Bugfix : Compat issues for Post Thumbnails under WP3.0
|
||||
* Bugfix : Esc_URL in Media RSS
|
||||
|
||||
= V1.5.3 - 11.04.2010 =
|
||||
* New : Adding pagination to footer
|
||||
* Changed : Perpare new filter to replace slideshow
|
||||
* Bugfix : Remove non-breaking space from navigation
|
||||
* Bugfix : Pagination of galleries
|
||||
* Bugfix : Fixed brackets position for old shortcode query
|
||||
* Bugfix : Slideshow option 'Show next image on click" has wrong default value
|
||||
|
||||
= V1.5.2 - 25.03.2010 =
|
||||
* Bugfix : XSS security vulnerability (THX to Core Security Advisories Team , Pedro Varangot)
|
||||
* Bugfix : Missing $wpdb in shortcodes.php
|
||||
|
||||
= V1.5.1 - 23.03.2010 =
|
||||
* Bugfix : PHP4 compat issue for Add gallery & options page
|
||||
* Bugfix : Gallery widget can now have a empty title
|
||||
* Bugfix : Adding correct stripslash for gallery title
|
||||
|
||||
= V1.5.0 - 18.03.2010 =
|
||||
* NEW : Support for Post thumbnail feature
|
||||
* NEW : Backup and Recover function for images (THX to Simone Fumagalli)
|
||||
* NEW : Resize images after upload (THX to Simone Fumagalli)
|
||||
* NEW : Added a JSON class for fetching galleries in a RESTful way (see xml/json.php)
|
||||
* NEW : Adding various new capabilities for user roles
|
||||
* NEW : Auto downloader for translation file
|
||||
* Changed : Rename query var from slideshow to callback for compat reason with other plugin
|
||||
* Changed : Convert widget function to new WP structure
|
||||
* Changed : Include lookup for tags into the backend search
|
||||
* Changed : Restructure addgallery and settings page to enable custom tabs
|
||||
* Bugfix : Select album preview from gallery preview pics instead random list
|
||||
* Bugfix : Keep fix dimension in edit thumbnail operation
|
||||
* Bugfix : Import meta data didn't work correct for existing images
|
||||
* Bugfix : Fix onload bug for Chrome 4 in Shutter script
|
||||
* Bugfix : Remove various PHP notices for a better world
|
||||
* Removed : Canonical link is now part of Wordpress 2.9
|
||||
|
||||
== Upgrade Notice ==
|
||||
|
||||
= 1.5.5 =
|
||||
* Compatibility issue for post thumbnails with WP2.9 and WP3.0. No Database changes...
|
||||
@@ -0,0 +1,460 @@
|
||||
=== NextGEN Gallery ===
|
||||
Contributors: photocrati
|
||||
Tags:gallery,image,images,photo,photos,picture,pictures,slideshow,flash,media,thumbnails,photo-albums,nextgen-gallery,nextgen
|
||||
Requires at least: 3.5
|
||||
Tested up to: 3.5.1
|
||||
Stable tag: trunk
|
||||
License: GPLv2
|
||||
|
||||
The most popular WordPress gallery plugin and one of the most popular plugins of all time with over 6 million downloads.
|
||||
|
||||
== Description ==
|
||||
|
||||
= WordPress Gallery Plugin =
|
||||
|
||||
NextGEN Gallery is the most popular **WordPress gallery plugin**, and one of the most popular WordPress plugins of all time, with over 6 million downloads.
|
||||
|
||||
It provides a powerful engine for uploading and managing galleries of images, with the ability to batch upload, import meta data, add/delete/rearrange/sort images, edit thumbnails, group galleries into albums, and more. It also provides two front-end display styles (slideshows and thumbnail galleries), both of which come with a wide array of options for controlling size, style, timing, transitions, controls, lightbox effects, and more.
|
||||
|
||||
*The NextGEN Gallery WordPress gallery plugin is now proudly maintained by <a href='http://www.photocrati.com'>Photocrati Media</a>. Special thanks to Alex Rabe who created and maintained NextGEN from 2007 through 2011.*
|
||||
|
||||
|
||||
= NextGEN WordPress Gallery Plugin Features =
|
||||
|
||||
|
||||
*Upload Galleries*
|
||||
|
||||
* Our WordPress gallery plugin offers diverse and powerful functionality for getting images from your desktop to your website. You can easily upload batches of images via a standard WordPress-style uploader, or upload images via zip file or FTP. NextGEN will automatically import your images meta data.
|
||||
|
||||
*Manage Galleries*
|
||||
|
||||
* Centralized gallery management. Enjoy a single location where you can see and manage all your galleries.
|
||||
* Edit galleries. Add or exclude images, change gallery title and description, reorder of images, resize thumbnails.
|
||||
* Thumbnail Management. Turn thumbnail cropping on and off, customize how individual thumbnails are cropped, and bulk resize thumbnails across one or more galleries.
|
||||
* Edit Individual Images. Edit meta data and image tags, rotate images, and exclude images.
|
||||
* Watermarks. Quickly add watermarks to batches or galleries of images.
|
||||
* Albums. Create and organize collections of galleries, and display them in either compact or extended format.
|
||||
|
||||
*Display Galleries*
|
||||
|
||||
* Two Gallery Types. Choose between two main display styles: Slideshow and Thumbnail, and allow visitors to toggle between the two.
|
||||
* Slideshow Galleries. Choose from a vast array of options for slideshows, including slideshow size, transition style, speed, image order, and optional navigation bar.
|
||||
* Thumbnail Galleries. Choose from a wide range of options to customize thumbnail galleries, including 5 different lightboxes for individual images, optional thumbnail cropping and editing, thumbnail styles, captions, and more.
|
||||
* Single Image Displays. Display and format single images.
|
||||
* Work with Options Panel or Shortcodes.
|
||||
|
||||
= NextGEN WordPress Gallery Plugin Community & Extensions =
|
||||
|
||||
NextGEN has been the dominant WordPress gallery plugin for years. As a result, there is large and great community of users and developers, as well as a large number of dedicated extension plugins. For a list of extension plugins, just search for NextGEN in the WordPress.org plugin repository, or visit our <a href="http://www.nextgen-gallery.com/nextgen-gallery-extension-plugins/">Complete List of NextGEN Extension Plugins</a>.
|
||||
|
||||
= NextGEN WordPress Gallery Plugin Resources =
|
||||
|
||||
*Visit the NextGEN <a href="http://www.nextgen-gallery.com" target="_blank">WordPress Gallery Plugin</a> official homepage<br>
|
||||
*View <a href="http://www.nextgen-gallery.com/nextgen-gallery-demos/" target="_blank">NextGEN Gallery Demos</a><br>
|
||||
*See the <a href="http://www.nextgen-gallery.com/nextgen-gallery-extension-plugins/">Complete List of NextGEN Extension Plugins</a><br>
|
||||
*Get <a href="http://wordpress.org/tags/nextgen-gallery?forum_id=10" target="_blank">NextGEN Support</a> via the WordPress.org forums<br>
|
||||
*Get <a href="http://www.nextgen-gallery.com/languages/" target="_blank">Translations</a> for your own language<br>
|
||||
*See <a href="http://www.photocrati.com/photography-wordpress-themes" target="_blank">WordPress Photography Themes</a> by the same author<br>
|
||||
*Follow NextGEN Gallery on <a title="Follow NextGEN Gallery on Facebook" href="http://www.facebook.com/NextGENGallery" target="_blank">Facebook</a>, <a title="Follow NextGEN Gallery on Twitter" href="http://twitter.com/NextGENGallery" target="_blank">Twitter</a>, and <a title="Follow NextGEN Gallery on Google +" href="http://plus.google.com/101643895780935290171" target="_blank">Google +</a><br>
|
||||
|
||||
|
||||
== Credits ==
|
||||
|
||||
Copyright:<br>
|
||||
Photocrati Media 2012<br>
|
||||
Alex Rabe 2007-2011
|
||||
|
||||
This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
** Please note **
|
||||
|
||||
NextGEN Gallery's flash slideshow option is powered by the JW Image Rotator from Long Tail Video. The Image Rotator is provided free as part of our plugin package thanks to a special commercial license with Long Tail Video. It is NOT released under GNU General Public License, and cannot be redistributed. A free version of the Image Rotator was previously available under a Creative Commons License, but it has been discontinued. Over time, we will be moving away from reliance on this file. For more information, see the Long Tail Video website: http://www.longtailvideo.com.
|
||||
|
||||
== Installation ==
|
||||
|
||||
1. Download, upload and install .zip under Plugins >> Add New > Upload, and activate the NextGEN Gallery WordPress gallery plugin.
|
||||
|
||||
2. From your Wordpress Dashboard, go to Gallery > Add Gallery/Images > Follow the on-screen cues.
|
||||
|
||||
3. Go to a post/page, and select the NextGEN Gallery button from the Kitchen Sink. Follow the on-screen cues to select, adjust, and publish your gallery.
|
||||
|
||||
That's it ... have fun! For more information, feel free to visit the official website for the NextGEN Gallery <a href="http://www.nextgen-gallery.com" target="_blank">WordPress Gallery Plugin</a>.
|
||||
|
||||
http://www.youtube.com/watch?v=Le_ZsNSuIvM
|
||||
|
||||
== Screenshots ==
|
||||
|
||||
1. Screenshot Admin Area
|
||||
2. Screenshot Album Selection
|
||||
3. Screenshot Shutter Effect
|
||||
4. Screenshot Watermark function
|
||||
5. Screenshot Flexible template layout
|
||||
6. Screenshot Show Exif data
|
||||
|
||||
== Shortcode ==
|
||||
|
||||
= Examples =
|
||||
|
||||
*Use Image Tags to Create Galleries/Albums* - [ nggtags album=WordPress,Cologne,Ireland ]
|
||||
|
||||
*Display Captions in Thumbnail Galleries* - [ nggallery id=1 template=caption ]
|
||||
|
||||
*Basic Filmstrip Galleries* - [ nggallery id=2 template=carousel images=7 ]
|
||||
|
||||
*Display Exif Data* - [ imagebrowser id=28 template=exif ]
|
||||
|
||||
*Sort Images in a Gallery Based on Their Tags* - [ nggtags gallery=cologne,wordpress,.. ]
|
||||
|
||||
*Add Tag Clouds* - [ tagcloud]
|
||||
|
||||
*Single Pic Options* - [ singlepic id=x w=width h=height mode=web20|watermark float=left|right ]
|
||||
|
||||
*Template Engine for Gallery Types*<br>
|
||||
[ nggallery id=1 template=sample1 ]<br>
|
||||
[ nggallery id=1 template=sample2 ]<br>
|
||||
[ nggallery id=1 template=sample3 ]<br>
|
||||
[ nggallery id=1 template=sample4 ]<br>
|
||||
[ nggallery id=1 template=sample5 ]<br>
|
||||
[ nggallery id=1 template=sample6 ]<br>
|
||||
|
||||
*Integration with Third Party Plugins*<br>
|
||||
[ monoslideshow id=1 w=450 h=350 ]<br>
|
||||
[ nggallery id=1 template=galleryview images=0 ]<br>
|
||||
[ media id=6 width=320 height=240 plugins=revolt-1 ]<br>
|
||||
[ media id=3 width=320 height=240 plugins=rateit-2 ]<br>
|
||||
|
||||
For more information, feel free to visit the official website for the NextGEN Gallery <a href="http://www.nextgen-gallery.com" target="_blank">WordPress Gallery Plugin</a>.
|
||||
|
||||
== Frequently Asked Questions ==
|
||||
|
||||
= Will NextGEN Gallery work with my theme? =
|
||||
|
||||
Part of what makes the NextGEN Gallery WordPress gallery plugin so popular is its flexibility - it works with the vast majority of premium and free themes, without requiring any coding.
|
||||
|
||||
|
||||
= Are the galleries flash based? =
|
||||
|
||||
No, NextGEN Gallery uses Javascript (J-Query) based displays to ensure compatibility across the widest range of displays possible.
|
||||
|
||||
|
||||
= Are the galleries mobile friendly? =
|
||||
|
||||
Yes, since we use Javascript rather than flash, NextGEN Gallery is compatible with Android, iOS, and Blackberry.
|
||||
|
||||
|
||||
= What is the difference between a gallery and an album? =
|
||||
|
||||
In the simplest of terms, Galleries contain your images and Albums contain your Galleries. Albums act as links and placeholders to quickly and easily navigate your galleries - Galleries will actually display your images.
|
||||
|
||||
|
||||
= Can I upload multiple images at once? =
|
||||
|
||||
Yes, you can batch upload entire galleries at a time.
|
||||
|
||||
|
||||
= Can I password protect galleries? =
|
||||
|
||||
Yes, WordPress allows you to password protect pages by default - which includes all galleries and content for the entire page. Password protection of pages can be turned on and off at any time, with just a few clicks.
|
||||
|
||||
|
||||
= Can I add a watermark to the images/slideshows? =
|
||||
|
||||
Yes, you can add text or image watermarks to your gallery images.
|
||||
|
||||
|
||||
= Can I crop thumbnails? =
|
||||
|
||||
Yes, each thumbnail image can be individually adjusted to suit your needs.
|
||||
|
||||
|
||||
= Is there pagination for galleries? =
|
||||
|
||||
Yes, and you can adjust the amount of images to be shown on a page at any time.
|
||||
|
||||
|
||||
= Can I customize the lightbox? =
|
||||
|
||||
Yes, the lightbox can be configured with multiple options directly from the Dashboard, and there are multiple CSS styles which can be applied and modified as well.
|
||||
|
||||
|
||||
= Can I add HTML to the captions? =
|
||||
|
||||
Yes, caption areas are fully HMTL capable.
|
||||
|
||||
|
||||
= Can I add an external links to galleries? =
|
||||
|
||||
Since the captions are fully HTML capable, you can add external links and any other type of mark up you wish.
|
||||
|
||||
|
||||
= Is NextGEN Gallery available in foreign languages? =
|
||||
|
||||
Yes, the NextGEN Gallery WordPress gallery plugin has been translated into dozens of languages - <a href="http://www.nextgen-gallery.com/languages/" target="_blank">click here to find out more.</a>
|
||||
|
||||
= More Information =
|
||||
|
||||
For more information, feel free to visit the official website for the NextGEN Gallery <a href="http://www.nextgen-gallery.com" target="_blank">WordPress Gallery Plugin</a>.
|
||||
|
||||
|
||||
== Changelog ==
|
||||
|
||||
= V1.9.13 - 06.11.2013 =
|
||||
* NEW: Slideshows are now centered to their content area
|
||||
* Secured: Ensure that only logged in users can upload images
|
||||
* Fixed: Import date is presered are no longer Jan 1 1970
|
||||
* Fixed: Removed mention of upgrade.php, which no longer exists
|
||||
|
||||
= V1.9.12 - 02.15.2013 =
|
||||
* Fixed: jQuery Conflict Detection was trying to dequeue irremovable scripts
|
||||
|
||||
= V1.9.11 - 02.12.2013 =
|
||||
* NEW: Added the ability to detect JQuery conflicts on NGG Admin Pages and auto-resolve
|
||||
* Changed: Added "nggalbum" shortcode. Use this when Jetpack is installed.
|
||||
* Changed: Using natural sorting algorithm for alphanumeric values
|
||||
* Changed: Database schema is automatically updated when out-of-date
|
||||
* Fixed: Fixed several incompatibility issues with Jetpack
|
||||
* Fixed: Empty drop-down for "Page Link To"
|
||||
* Fixed: Alphabetical image sorting
|
||||
* Fixed: Compatibility with Arjuna X theme
|
||||
* Fixed: “Creating default object from empty value” on album page
|
||||
* Fixed: Compatibility issues with PHP 5.4 on album page
|
||||
* Fixed: E_DEPRECATED warning when using get_userdatabylogin() function
|
||||
* Fixed: Removed many E_NOTICE errors
|
||||
* Fixed: Correct use of register_uninstall_hook across all PHP versions
|
||||
|
||||
= V1.9.10 - 12.18.2012 =
|
||||
* Fixed: XML-RPC error displayed when authenticating using WordPress 3.5
|
||||
* Fixed: Restored compatibility with NextGEN Gallery Export Plugin
|
||||
* Fixed: Removed some remaining references to database upgrade code
|
||||
* Fixed: Deleted galleries within an album are handed gracefully without warning messages
|
||||
* Fixed: Correct use of register_uninstall_hook
|
||||
* Fixed: CSS and usability issues with the TinyMCE window used to display galleries
|
||||
|
||||
* NEW: JW ImageRotator v3.17 is now bundled with the plugin and used by default.
|
||||
* Changed: Removed database upgrade code for versions of NextGEN Gallery earlier than 1.9.3
|
||||
* Fixed: Compatibility with WordPress v3.5 ( wpdb->prepare() warnings )
|
||||
* Fixed: Sorting by filename now produces expected results using a natural sorting algorithm
|
||||
|
||||
= V1.9.8 - 12.05.2012 =
|
||||
* Secured: Removed bundled version of swfupload. See fix below for SCM information.
|
||||
* Changed: All transients created by NextGEN are flushed when the plugin is activated.
|
||||
* Fixed: Our primary SCM is conducted at http://bitbucket.org/photocrati/nextgen-gallery, but was not synchronizing correctly with the WordPress Plugin SVN Repository
|
||||
* Fixed: The transient adjustment fixes: http://wordpress.org/support/topic/plugin-nextgen-gallery-_transient_ngg_request-entry-in-wp_options
|
||||
|
||||
= V1.9.7 - 11.13.2012 =
|
||||
* Secured: Removed bundled version of swfupload; using WordPress-bundled version instead for WordPress 3.2 instances
|
||||
* Changed: Using JQuery UI for the image sorting interface (thanks Tomás Soler)
|
||||
* Bugfix: Image uploads work in WP 3.2 when using Safari
|
||||
* Bugfix: Adjusted TinyMCE window to use built-in JavaScript libraries
|
||||
* Bugfix: Removed Photocrati acquisition announcement
|
||||
* Bugfix: Fixed incorrect usage of ImageJpeg() function
|
||||
* Bugfix: Switched from "template_redirect" to "wp_enqueue_script" hook to load scripts and styles
|
||||
|
||||
= V1.9.6 - 07.21.2012 =
|
||||
* Changed: Implemented workaround for bug found in WordPress SEO, resulting in no images being added to sitemap
|
||||
* Bugfix: Fixed an issue with users not being able to dismiss the "Photocrati Acquisition Notice"
|
||||
* Bugfix: Adjusted Javascript for activating social media pages to load on NextGEN Gallery pages only.
|
||||
* Bugfix: Fixed compatibility issue with Simple Facebook Connect
|
||||
* Bugfix: Using correct Facebook Page ID in Like button
|
||||
|
||||
= V1.9.5 - 18.07.2012 =
|
||||
* Changed: Branding changes following Photocrati acquisition (removed donation messages and updated links)
|
||||
* Secured: Use WordPress-bundled JavaScript libraries for swfobject and swfupload instead of bundling our own
|
||||
* Bugfix: Adjusted thickbox effect styling to ensure that the lightbox is always displayed in the foreground
|
||||
* Bugfix: Fixed compatibility issues with Contact Form 7 and other plugins by following WordPress Plugin conventions
|
||||
* Bugfix: Fixed network-wide activation in WordPress 3.4
|
||||
* Bugfix: Plugin is no longer dependent on it's folder name
|
||||
|
||||
= V1.9.3 - 26.02.2012 =
|
||||
* Bugfix : Ensure to set the slug for "all" albums
|
||||
* Bugfix : Updated german translation ( THX to Roger Hunziker )
|
||||
* Bugfix : Ensure error checking on IPTC array (THX to Kristian Edlund)
|
||||
* Bugfix : Handle IE8 cached images better in slideshow
|
||||
* Bugfix : Show album preview image if selected (THX to Kristian Edlund)
|
||||
|
||||
= V1.9.2 - 17.01.2012 =
|
||||
* NEW : Added more XMLRPC commands (THX to Vladimir Vinogradsky)
|
||||
* Changed : Rework Post-thumbnail function (THX to Kristian Edlund)
|
||||
* Bugfix : Check first for valid images on unzip (only Mac OS zip-files)
|
||||
* Bugfix : Increase z-index for twenty eleven theme
|
||||
* Bugfix : Support non latin chars in tagcloud
|
||||
* Bugfix : Allow other tinymce intance
|
||||
* Bugfix : Better support for WPML translation
|
||||
|
||||
= V1.9.1 - 10.12.2011 =
|
||||
* Bugfix : Security hardness for untrusted filenames/meta data (THX to Brian St. Pierre)
|
||||
* Bugfix : Fixed security vulnerability (TXH to Jon Cave)
|
||||
* Bugfix : Load piclens script via other function
|
||||
* Bugfix : IE7 script fix for add gallery
|
||||
* Bugfix : IE7/IE8 width set correctly for edit album autocomplete field
|
||||
|
||||
= V1.9.0 - 27.11.2011 =
|
||||
* NEW : Keep images transparency for PNG and GIF format
|
||||
* NEW : Switch to Plupload, support now HTML5 Upload (only with WordPress 3.3)
|
||||
* NEW : Added client side resize feature (only with WordPress 3.3)
|
||||
* NEW : Support for gallery templates in album shortcodes [ album id=x template="name" gallery="templatename" ]
|
||||
* NEW : Added new hook ngg_delete_picture
|
||||
* Changed : Updated to jQuery Cycle Version 2.9995
|
||||
* Changed : Always cache the single pictures, remove option
|
||||
* Bugfix : Couldn't use bulk operation for search results
|
||||
* Bugfix : Bugfix for Edit thumbnails under IE 8 + 9
|
||||
* Bugfix : Allow empty altext in ngg.editImage
|
||||
* Bugfix : Various PHP notice fixes
|
||||
* Bugfix : Resize fix for Shutter effect and mobile Browser
|
||||
* Bugfix : FTP Import missing slug field into database
|
||||
* Bugfix : Check also EXIF field "DateTimeOriginal" for timestamp
|
||||
|
||||
= V1.8.4 - 26.10.2011 =
|
||||
* Bugfix : Fixed security vulnerability (TXH to Alain Schneider)
|
||||
|
||||
= V1.8.3 - 07.08.2011 =
|
||||
* Changed : Support for simple custom permalink structures (i.e. /%category%/%postname%/)
|
||||
* Bugfix : Sub-Albums in Albums didn't create the correct link
|
||||
* Bugfix : AJAX Pagination didn't work anymore
|
||||
* Bugfix : Adding index.php to home_url()
|
||||
* Bugfix : Preview picture lost on backend gallery page 2 or higher
|
||||
|
||||
= V1.8.2 - 12.07.2011 =
|
||||
* Bugfix : Set pagination variables for search result, otherwise update failed
|
||||
* Bugfix : Update failed for paged galleries since WordPress 3.2
|
||||
|
||||
= V1.8.1 - 18.06.2011 =
|
||||
* Bugfix : Special case for pagination, instead of showing page-1, we show the clean url
|
||||
* Bugfix : Various PHP notice fixes
|
||||
* Bugfix : Typo in rewrite rules
|
||||
* Bugfix : Flush rewrite rules during upgrade later
|
||||
|
||||
= V1.8.0 - 12.06.2011 =
|
||||
* NEW : Full rework of permalink url structure
|
||||
* NEW : Adding Google Sitemaps for Images (require WordPress SEO plugin by YOAST )
|
||||
* NEW : Support for WPML ( WordPress Multilingual Plugin )
|
||||
* NEW : Adding support for arrow key in shutter effect (THX to Flyvans)
|
||||
* NEW : Adding sort operation for galleries overview page
|
||||
* Changed : Updated pagination to new WP3.1 style
|
||||
* Bugfix : Create unique slug in a better way
|
||||
* Bugfix : Rework screen options filter for gallery and image table
|
||||
* Bugfix : Empty values in XMLRPC update calls are ignored
|
||||
* Bugfix : Create gallery failed when safe-mode on
|
||||
* Bugfix : Permalink didn't work in combination with album & imagebrowser
|
||||
|
||||
= V1.7.4 - 15.02.2011 =
|
||||
* Bugfix : Disallow direct call of ajax file to avoid path disclosure (THX to High-Tech Bridge SA)
|
||||
* Bugfix : Rework jQuery Cycle slideshow for IE compat reason (THX to Justin Dickenson)
|
||||
* Bugfix : Resize only larger images in slideshow
|
||||
* Bugfix : Improved image format detection in gd.thumbnail class (THX to Kupar.b)
|
||||
|
||||
= V1.7.3 - 20.01.2011 =
|
||||
* NEW : Introduce plugin health check for conflicts with other plugins/themes
|
||||
* NEW : Adding new XMLRPC method ngg.deleteImage
|
||||
* NEW : Adding new XMLRPC method ngg.editImage
|
||||
* Changed : Rework register script for autocomplete feature
|
||||
* Bugfix : Bugfix for Multisite setup and flash upload
|
||||
* Bugfix : WP3.1 compat issue, show site admin page only on Multisite installation
|
||||
|
||||
= V1.7.2 - 13.12.2010 =
|
||||
* Bugfix : Adding images to database require slug (NOT NULL)
|
||||
|
||||
= V1.7.1 - 13.12.2010 =
|
||||
* Changed : Disable upgrade for PHP4 user
|
||||
* Changed : Disable colorpicker for option page
|
||||
* Bugfix : Compat fix for upgrade
|
||||
|
||||
= V1.7.0 - 11.12.2010 =
|
||||
* NEW : Publish a new post direct from the gallery admin page
|
||||
* NEW : Added filter hook 'ngg_get_image_metadata' to add more exif/iptc information
|
||||
* NEW : Adding Autocomplete field to TinyMCE Popup and Album page
|
||||
* NEW : More methods for XMLRPC interface
|
||||
* Changed : New hooks for gallery table (THX to Alexander Schneider)
|
||||
* Changed : Introduce jQuery dialog as new UI element
|
||||
* Changed : Call TinyMCE window via admin-ajax
|
||||
* Bugfix : Better support for SSL blogs
|
||||
* Bugfix : Install/Upgrade failed when table prefix contain captial letters
|
||||
* Bugfix : Fix validation issues in Media-RSS
|
||||
* Bugfix : Empty tags in XMP Meta causes PHP error
|
||||
* Bugfix : Rework load mechanism for slideshow
|
||||
* Bugfix : Copy meta data when image is copied
|
||||
* Bugfix : Icon Support for Ozh' Admin Drop Down Menu
|
||||
* Bugfix : Use correct sort order in slideshow
|
||||
|
||||
= V1.6.2 - 19.09.2010 =
|
||||
* NEW : Added constant NGG_SKIP_LOAD_SCRIPTS to avoid script load
|
||||
* Bugfix : Load Tags library with core files
|
||||
* Bugfix : Slideshow script failed in IE7, load script now in header
|
||||
* Bugfix : Load slideshow widget always
|
||||
* Changed : New admin notice for database upgrade
|
||||
* Changed : Rework crop feature for featured images
|
||||
* Changed : Use site_url() instead get_option ('siteurl'), required for SSL support
|
||||
|
||||
= V1.6.1 - 08.09.2010 =
|
||||
* Bugfix : Script load of swfobject.js failed
|
||||
* Bugfix : Show sideshow also with 1 or 2 images
|
||||
* Bugfix : Rework null byte check in zip upload
|
||||
|
||||
= V1.6.0 - 07.09.2010 =
|
||||
* NEW : Wordpress 3.0 Network (Multi-Site) support
|
||||
* NEW : Integrate jQuery Cycle as NON-Flash slideshow
|
||||
* NEW : Adding jQuery File Tree for import folder (THX to Sergey Pasyuk )
|
||||
* NEW : Added action hook 'ngg_show_imagebrowser_first' on custom request
|
||||
* NEW : Added filter hook 'ngg_slideshow_size' to resize sildeshow for mobile browser plugins
|
||||
* Changed : Reorder tabs for upload
|
||||
* Changed : New menu icon and screen icon (THX to Ben Dunkle)
|
||||
* Changed : Load frontend libs always
|
||||
* Changed : Rework of overview page
|
||||
* Bugfix : Security bugfix for Zip-Upload (THX to Dominic Szablewski)
|
||||
* Bugfix : Allow JPG, PNG, GIF extension
|
||||
* Bugfix : New German translation (THX to Martin Kramarz)
|
||||
* Bugfix : Copy/Move also backup file
|
||||
* Bugfix : Calculate correct ratio for fix thumbnail size (THX to Alekz Keck)
|
||||
|
||||
= V1.5.5 - 14.06.2010 =
|
||||
* Bugfix : Compat issue for post thumbnails with WP2.9
|
||||
* NEW : Adding more hooks for custom fields plugin
|
||||
|
||||
= V1.5.4 - 14.06.2010 =
|
||||
* Bugfix : No resize of smaller images
|
||||
* Bugfix : Compat issues for Post Thumbnails under WP3.0
|
||||
* Bugfix : Esc_URL in Media RSS
|
||||
|
||||
= V1.5.3 - 11.04.2010 =
|
||||
* New : Adding pagination to footer
|
||||
* Changed : Perpare new filter to replace slideshow
|
||||
* Bugfix : Remove non-breaking space from navigation
|
||||
* Bugfix : Pagination of galleries
|
||||
* Bugfix : Fixed brackets position for old shortcode query
|
||||
* Bugfix : Slideshow option 'Show next image on click" has wrong default value
|
||||
|
||||
= V1.5.2 - 25.03.2010 =
|
||||
* Bugfix : XSS security vulnerability (THX to Core Security Advisories Team , Pedro Varangot)
|
||||
* Bugfix : Missing $wpdb in shortcodes.php
|
||||
|
||||
= V1.5.1 - 23.03.2010 =
|
||||
* Bugfix : PHP4 compat issue for Add gallery & options page
|
||||
* Bugfix : Gallery widget can now have a empty title
|
||||
* Bugfix : Adding correct stripslash for gallery title
|
||||
|
||||
= V1.5.0 - 18.03.2010 =
|
||||
* NEW : Support for Post thumbnail feature
|
||||
* NEW : Backup and Recover function for images (THX to Simone Fumagalli)
|
||||
* NEW : Resize images after upload (THX to Simone Fumagalli)
|
||||
* NEW : Added a JSON class for fetching galleries in a RESTful way (see xml/json.php)
|
||||
* NEW : Adding various new capabilities for user roles
|
||||
* NEW : Auto downloader for translation file
|
||||
* Changed : Rename query var from slideshow to callback for compat reason with other plugin
|
||||
* Changed : Convert widget function to new WP structure
|
||||
* Changed : Include lookup for tags into the backend search
|
||||
* Changed : Restructure addgallery and settings page to enable custom tabs
|
||||
* Bugfix : Select album preview from gallery preview pics instead random list
|
||||
* Bugfix : Keep fix dimension in edit thumbnail operation
|
||||
* Bugfix : Import meta data didn't work correct for existing images
|
||||
* Bugfix : Fix onload bug for Chrome 4 in Shutter script
|
||||
* Bugfix : Remove various PHP notices for a better world
|
||||
* Removed : Canonical link is now part of Wordpress 2.9
|
||||
|
||||
== Upgrade Notice ==
|
||||
|
||||
= 1.5.5 =
|
||||
* Compatibility issue for post thumbnails with WP2.9 and WP3.0. No Database changes...
|
||||
@@ -0,0 +1,5 @@
|
||||
Version: 141007
|
||||
Stable tag: 141007
|
||||
|
||||
Tested up to: 4.0
|
||||
Requires at least: 3.3
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user