Commit 8b5d0f46 authored by Liang Ding's avatar Liang Ding

Merge remote-tracking branch 'origin/0.4.6'

Conflicts:
	core/src/main/java/org/b3log/solo/util/Articles.java
	core/src/test/java/org/b3log/solo/repository/impl/UserRepositoryImplTestCase.java
	war/src/main/webapp/CHANGE_LOGS.html
	war/src/main/webapp/css/default-admin.css
	war/src/main/webapp/css/default-base.css
	war/src/main/webapp/css/default-init.css
	war/src/main/webapp/js/admin/admin.js
	war/src/main/webapp/js/admin/editorKindEditor.js
	war/src/main/webapp/js/admin/editorTinyMCE.js
	war/src/main/webapp/js/admin/pageList.js
	war/src/main/webapp/js/admin/preference.js
	war/src/main/webapp/js/admin/tablePaginate.js
	war/src/main/webapp/js/lib/jquery/jquery.bowknot.min.js
	war/src/main/webapp/skins/classic/css/classic.css
parents c9216004 3fab14b0
...@@ -2,3 +2,4 @@ ...@@ -2,3 +2,4 @@
/core/target/ /core/target/
/war/gae/target/ /war/gae/target/
/war/target/ /war/target/
/war/mysql/target/
\ No newline at end of file
...@@ -5,6 +5,16 @@ ...@@ -5,6 +5,16 @@
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
</head> </head>
<body> <body>
<h2>Release 0.4.6 - Jul 1, 2012</h2>
<ul>
<li><a href="https://github.com/b3log/b3log-solo/issues/10">10 评论表情后台管理不显示</a></li>
<li><a href="https://github.com/b3log/b3log-solo/issues/12">12 编辑自定义导航报错</a></li>
<li><a href="https://github.com/b3log/b3log-solo/issues/15">15 sitemap.xml 导航生成重复</a></li>
<li><a href="https://github.com/b3log/b3log-solo/issues/17">17 默认皮肤改为 ease</a></li>
<li><a href="https://github.com/b3log/b3log-solo/issues/23">23 偏好设定关键参数校验</a></li>
<li><a href="https://github.com/b3log/b3log-solo/issues/27">27 自定义导航后台链接问题</a></li>
<li><a href="https://github.com/b3log/b3log-solo/issues/32">32 升级 FreeMarker 到 2.3.19</a></li>
</ul>
<h2>Release 0.4.5 - Jun 1, 2012</h2> <h2>Release 0.4.5 - Jun 1, 2012</h2>
<ul> <ul>
<li><a href="http://code.google.com/p/b3log-solo/issues/detail?id=302">302 文章加密</a></li> <li><a href="http://code.google.com/p/b3log-solo/issues/detail?id=302">302 文章加密</a></li>
......
...@@ -4,16 +4,16 @@ Project home: https://github.com/b3log/b3log-solo ...@@ -4,16 +4,16 @@ Project home: https://github.com/b3log/b3log-solo
Request features/Report bugs: https://github.com/b3log/b3log-solo/issues/new Request features/Report bugs: https://github.com/b3log/b3log-solo/issues/new
* QQ Qun: 13139268 * QQ Qun: 13139268
* User Guide: http://code.google.com/p/b3log-solo/wiki/UserGuide * User Guide: https://github.com/b3log/b3log-solo/wiki/Pre_installation
* Dev Guide: http://code.google.com/p/b3log-solo/wiki/pre_dev * Dev Guide: https://github.com/b3log/b3log-solo/wiki/Pre_dev
* Skin Dev Guide: http://code.google.com/p/b3log-solo/wiki/develop_steps * Skin Dev Guide: https://github.com/b3log/b3log-solo/wiki/Develop_steps
* Plugin Dev Guide: https://docs.google.com/document/pub?id=15H7Q3EBo-44v61Xp_epiYY7vK_gPJLkQaT7T1gkE64w&pli=1 * Plugin Dev Guide: https://docs.google.com/document/pub?id=15H7Q3EBo-44v61Xp_epiYY7vK_gPJLkQaT7T1gkE64w&pli=1
==== ====
B3log Index: http://b3log.org B3log Index: http://b3log.org
B3log Team: http://code.google.com/p/b3log-solo/wiki/about_us B3log Team: https://github.com/b3log/b3log-solo/wiki/About_us
Join B3log Team: http://code.google.com/p/b3log-solo/wiki/join_us Join B3log Team: https://github.com/b3log/b3log-solo/wiki/Join_us
==== ====
平等,自由,奔放 平等,自由,奔放
......
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<!-- <!--
Description: B3log Solo core. Description: B3log Solo core.
Version: 2.0.0.8, May 11, 2012 Version: 2.0.0.9, Jun 19, 2012
Author: Liang Ding Author: Liang Ding
--> -->
<project xmlns="http://maven.apache.org/POM/4.0.0" <project xmlns="http://maven.apache.org/POM/4.0.0"
...@@ -17,7 +17,7 @@ ...@@ -17,7 +17,7 @@
<parent> <parent>
<groupId>org.b3log</groupId> <groupId>org.b3log</groupId>
<artifactId>solo</artifactId> <artifactId>solo</artifactId>
<version>0.4.5</version> <version>0.4.6</version>
</parent> </parent>
<dependencies> <dependencies>
......
...@@ -52,7 +52,7 @@ import org.json.JSONObject; ...@@ -52,7 +52,7 @@ import org.json.JSONObject;
* B3log Solo servlet listener. * B3log Solo servlet listener.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.0.7.1, May 29, 2011 * @version 1.0.7.3, Jun 19, 2011
* @since 0.3.1 * @since 0.3.1
*/ */
public final class SoloServletListener extends AbstractServletListener { public final class SoloServletListener extends AbstractServletListener {
...@@ -60,7 +60,7 @@ public final class SoloServletListener extends AbstractServletListener { ...@@ -60,7 +60,7 @@ public final class SoloServletListener extends AbstractServletListener {
/** /**
* B3log Solo version. * B3log Solo version.
*/ */
public static final String VERSION = "0.4.5"; public static final String VERSION = "0.4.6";
/** /**
* Logger. * Logger.
*/ */
...@@ -84,8 +84,8 @@ public final class SoloServletListener extends AbstractServletListener { ...@@ -84,8 +84,8 @@ public final class SoloServletListener extends AbstractServletListener {
super.contextInitialized(servletContextEvent); super.contextInitialized(servletContextEvent);
// Default to skin "classic", loads from preference later // Default to skin "ease", loads from preference later
Skins.setDirectoryForTemplateLoading("classic"); Skins.setDirectoryForTemplateLoading("ease");
final PreferenceRepository preferenceRepository = PreferenceRepositoryImpl.getInstance(); final PreferenceRepository preferenceRepository = PreferenceRepositoryImpl.getInstance();
......
...@@ -194,7 +194,7 @@ public final class Preference { ...@@ -194,7 +194,7 @@ public final class Preference {
* Default preference. * Default preference.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.1.0.6, Mar 28, 2012 * @version 1.1.0.7, Jun 12, 2012
* @since 0.3.1 * @since 0.3.1
*/ */
public static final class Default { public static final class Default {
...@@ -238,7 +238,7 @@ public final class Preference { ...@@ -238,7 +238,7 @@ public final class Preference {
/** /**
* Default skin directory name. * Default skin directory name.
*/ */
public static final String DEFAULT_SKIN_DIR_NAME = "classic"; public static final String DEFAULT_SKIN_DIR_NAME = "ease";
/** /**
* Default language. * Default language.
*/ */
......
...@@ -770,6 +770,7 @@ public final class ArticleProcessor { ...@@ -770,6 +770,7 @@ public final class ArticleProcessor {
@RequestProcessing(value = "/article", method = HTTPRequestMethod.GET) @RequestProcessing(value = "/article", method = HTTPRequestMethod.GET)
public void showArticle(final HTTPRequestContext context, final HttpServletRequest request, final HttpServletResponse response) public void showArticle(final HTTPRequestContext context, final HttpServletRequest request, final HttpServletResponse response)
throws IOException { throws IOException {
// See PermalinkFiler#dispatchToArticleOrPageProcessor()
final JSONObject article = (JSONObject) request.getAttribute(Article.ARTICLE); final JSONObject article = (JSONObject) request.getAttribute(Article.ARTICLE);
if (null == article) { if (null == article) {
response.sendError(HttpServletResponse.SC_NOT_FOUND); response.sendError(HttpServletResponse.SC_NOT_FOUND);
......
...@@ -28,7 +28,10 @@ import org.b3log.latke.annotation.RequestProcessor; ...@@ -28,7 +28,10 @@ import org.b3log.latke.annotation.RequestProcessor;
import org.b3log.latke.service.LangPropsService; import org.b3log.latke.service.LangPropsService;
import org.b3log.latke.servlet.HTTPRequestContext; import org.b3log.latke.servlet.HTTPRequestContext;
import org.b3log.latke.servlet.HTTPRequestMethod; import org.b3log.latke.servlet.HTTPRequestMethod;
import org.b3log.latke.user.UserService;
import org.b3log.latke.user.UserServiceFactory;
import org.b3log.latke.util.Locales; import org.b3log.latke.util.Locales;
import org.b3log.solo.model.Common;
import org.b3log.solo.processor.renderer.ConsoleRenderer; import org.b3log.solo.processor.renderer.ConsoleRenderer;
import org.b3log.solo.processor.util.Filler; import org.b3log.solo.processor.util.Filler;
import org.b3log.solo.service.PreferenceQueryService; import org.b3log.solo.service.PreferenceQueryService;
...@@ -38,7 +41,7 @@ import org.json.JSONObject; ...@@ -38,7 +41,7 @@ import org.json.JSONObject;
* Error processor. * Error processor.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.0.0.0, May 18, 2012 * @version 1.0.0.1, Jun 20, 2012
* @since 0.4.5 * @since 0.4.5
*/ */
@RequestProcessor @RequestProcessor
...@@ -60,6 +63,10 @@ public final class ErrorProcessor { ...@@ -60,6 +63,10 @@ public final class ErrorProcessor {
* Language service. * Language service.
*/ */
private LangPropsService langPropsService = LangPropsService.getInstance(); private LangPropsService langPropsService = LangPropsService.getInstance();
/**
* User service.
*/
private static UserService userService = UserServiceFactory.getUserService();
/** /**
* Shows the user template page. * Shows the user template page.
...@@ -90,6 +97,8 @@ public final class ErrorProcessor { ...@@ -90,6 +97,8 @@ public final class ErrorProcessor {
filler.fillBlogHeader(request, dataModel, preference); filler.fillBlogHeader(request, dataModel, preference);
filler.fillBlogFooter(dataModel, preference); filler.fillBlogFooter(dataModel, preference);
dataModel.put(Common.LOGIN_URL, userService.createLoginURL(Common.ADMIN_INDEX_URI));
} catch (final Exception e) { } catch (final Exception e) {
LOGGER.log(Level.SEVERE, e.getMessage(), e); LOGGER.log(Level.SEVERE, e.getMessage(), e);
......
...@@ -29,6 +29,7 @@ import org.b3log.latke.annotation.RequestProcessing; ...@@ -29,6 +29,7 @@ import org.b3log.latke.annotation.RequestProcessing;
import org.b3log.latke.annotation.RequestProcessor; import org.b3log.latke.annotation.RequestProcessor;
import org.b3log.latke.model.User; import org.b3log.latke.model.User;
import org.b3log.latke.repository.FilterOperator; import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.PropertyFilter;
import org.b3log.latke.repository.Query; import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.SortDirection; import org.b3log.latke.repository.SortDirection;
import org.b3log.latke.servlet.HTTPRequestContext; import org.b3log.latke.servlet.HTTPRequestContext;
...@@ -125,7 +126,7 @@ public final class FeedProcessor { ...@@ -125,7 +126,7 @@ public final class FeedProcessor {
final Query query = new Query().setCurrentPageNum(1). final Query query = new Query().setCurrentPageNum(1).
setPageSize(ENTRY_OUTPUT_CNT). setPageSize(ENTRY_OUTPUT_CNT).
addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true). setFilter(new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true)).
addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING). addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING).
setPageCount(1); setPageCount(1);
...@@ -335,7 +336,7 @@ public final class FeedProcessor { ...@@ -335,7 +336,7 @@ public final class FeedProcessor {
final Query query = new Query().setCurrentPageNum(1). final Query query = new Query().setCurrentPageNum(1).
setPageSize(ENTRY_OUTPUT_CNT). setPageSize(ENTRY_OUTPUT_CNT).
addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true). setFilter(new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true)).
addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING). addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING).
setPageCount(1); setPageCount(1);
......
...@@ -111,6 +111,7 @@ public final class PageProcessor { ...@@ -111,6 +111,7 @@ public final class PageProcessor {
final Map<String, String> langs = langPropsService.getAll(Latkes.getLocale()); final Map<String, String> langs = langPropsService.getAll(Latkes.getLocale());
request.setAttribute(CACHED_TYPE, langs.get(PageTypes.PAGE)); request.setAttribute(CACHED_TYPE, langs.get(PageTypes.PAGE));
// See PermalinkFiler#dispatchToArticleOrPageProcessor()
final JSONObject page = (JSONObject) request.getAttribute(Page.PAGE); final JSONObject page = (JSONObject) request.getAttribute(Page.PAGE);
if (null == page) { if (null == page) {
response.sendError(HttpServletResponse.SC_NOT_FOUND); response.sendError(HttpServletResponse.SC_NOT_FOUND);
......
...@@ -26,6 +26,7 @@ import org.b3log.latke.Keys; ...@@ -26,6 +26,7 @@ import org.b3log.latke.Keys;
import org.b3log.latke.annotation.RequestProcessing; import org.b3log.latke.annotation.RequestProcessing;
import org.b3log.latke.annotation.RequestProcessor; import org.b3log.latke.annotation.RequestProcessor;
import org.b3log.latke.repository.FilterOperator; import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.PropertyFilter;
import org.b3log.latke.repository.Query; import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.SortDirection; import org.b3log.latke.repository.SortDirection;
import org.b3log.latke.servlet.HTTPRequestContext; import org.b3log.latke.servlet.HTTPRequestContext;
...@@ -53,7 +54,7 @@ import org.json.JSONObject; ...@@ -53,7 +54,7 @@ import org.json.JSONObject;
* Site map (sitemap) processor. * Site map (sitemap) processor.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.0.0.3, May 7, 2012 * @version 1.0.0.4, Jun 11, 2012
* @since 0.3.1 * @since 0.3.1
*/ */
@RequestProcessor @RequestProcessor
...@@ -100,7 +101,7 @@ public final class SitemapProcessor { ...@@ -100,7 +101,7 @@ public final class SitemapProcessor {
final JSONObject preference = preferenceQueryService.getPreference(); final JSONObject preference = preferenceQueryService.getPreference();
addArticles(sitemap, preference); addArticles(sitemap, preference);
addPages(sitemap, preference); addNavigations(sitemap, preference);
addTags(sitemap, preference); addTags(sitemap, preference);
addArchives(sitemap, preference); addArchives(sitemap, preference);
...@@ -113,7 +114,6 @@ public final class SitemapProcessor { ...@@ -113,7 +114,6 @@ public final class SitemapProcessor {
try { try {
context.getResponse().sendError(HttpServletResponse.SC_SERVICE_UNAVAILABLE); context.getResponse().sendError(HttpServletResponse.SC_SERVICE_UNAVAILABLE);
return;
} catch (final IOException ex) { } catch (final IOException ex) {
throw new RuntimeException(ex); throw new RuntimeException(ex);
} }
...@@ -132,7 +132,7 @@ public final class SitemapProcessor { ...@@ -132,7 +132,7 @@ public final class SitemapProcessor {
// XXX: query all articles? // XXX: query all articles?
final Query query = new Query().setCurrentPageNum(1). final Query query = new Query().setCurrentPageNum(1).
addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true). setFilter(new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true)).
addSort(Article.ARTICLE_CREATE_DATE, SortDirection.DESCENDING); addSort(Article.ARTICLE_CREATE_DATE, SortDirection.DESCENDING);
// Closes cache avoid Java heap space out of memory while caching // Closes cache avoid Java heap space out of memory while caching
...@@ -160,13 +160,13 @@ public final class SitemapProcessor { ...@@ -160,13 +160,13 @@ public final class SitemapProcessor {
} }
/** /**
* Adds pages into the specified sitemap. * Adds navigations into the specified sitemap.
* *
* @param sitemap the specified sitemap * @param sitemap the specified sitemap
* @param preference the specified preference * @param preference the specified preference
* @throws Exception exception * @throws Exception exception
*/ */
private void addPages(final Sitemap sitemap, final JSONObject preference) throws Exception { private void addNavigations(final Sitemap sitemap, final JSONObject preference) throws Exception {
final String host = preference.getString(Preference.BLOG_HOST); final String host = preference.getString(Preference.BLOG_HOST);
final JSONObject result = pageRepository.get(new Query()); final JSONObject result = pageRepository.get(new Query());
...@@ -176,7 +176,13 @@ public final class SitemapProcessor { ...@@ -176,7 +176,13 @@ public final class SitemapProcessor {
final String permalink = page.getString(Page.PAGE_PERMALINK); final String permalink = page.getString(Page.PAGE_PERMALINK);
final URL url = new URL(); final URL url = new URL();
// The navigation maybe a page or a link
// Just filters for user mistakes tolerance
if (!permalink.contains("://")) {
url.setLoc("http://" + host + permalink); url.setLoc("http://" + host + permalink);
} else {
url.setLoc(permalink);
}
sitemap.addURL(url); sitemap.addURL(url);
} }
......
...@@ -37,7 +37,7 @@ import org.json.JSONObject; ...@@ -37,7 +37,7 @@ import org.json.JSONObject;
* Upgrader. * Upgrader.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.1.0.9, Apr 29, 2012 * @version 1.1.1.0, Jun 19, 2012
* @since 0.3.1 * @since 0.3.1
*/ */
@RequestProcessor @RequestProcessor
...@@ -99,8 +99,8 @@ public final class UpgradeProcessor { ...@@ -99,8 +99,8 @@ public final class UpgradeProcessor {
return; return;
} }
if ("0.4.1".equals(version)) { if ("0.4.5".equals(version)) {
v041ToV045(); v045ToV046();
} else { } else {
final String msg = "Your B3log Solo is too old to upgrader, please contact the B3log Solo developers"; final String msg = "Your B3log Solo is too old to upgrader, please contact the B3log Solo developers";
LOGGER.warning(msg); LOGGER.warning(msg);
...@@ -114,54 +114,25 @@ public final class UpgradeProcessor { ...@@ -114,54 +114,25 @@ public final class UpgradeProcessor {
} }
/** /**
* Upgrades from version 041 to version 045. * Upgrades from version 045 to version 046.
* *
* <p>
* Model:
* <ul>
* <li>
* Adds a property(named {@value Article#ARTICLE_EDITOR_TYPE}) to entity {@link Article}
* </li>
* <li>
* Adds a property(named {@value Page#PAGE_EDITOR_TYPE}) to entity {@link Page}
* </li>
* <li>
* Adds a property(named {@value Preference#EDITOR_TYPE}) to entity {@link Preference}
* </li>
* </ul>
* </p>
* @throws Exception upgrade fails * @throws Exception upgrade fails
*/ */
private void v041ToV045() throws Exception { private void v045ToV046() throws Exception {
LOGGER.info("Upgrading from version 041 to version 045...."); LOGGER.info("Upgrading from version 045 to version 046....");
articleRepository.setCacheEnabled(false); articleRepository.setCacheEnabled(false);
Transaction transaction = null; Transaction transaction = null;
try { try {
upgradeArticles();
transaction = userRepository.beginTransaction(); transaction = userRepository.beginTransaction();
// Upgrades page model
final JSONObject result = pageRepository.get(new Query());
final JSONArray pages = result.getJSONArray(Keys.RESULTS);
for (int i = 0; i < pages.length(); i++) {
final JSONObject page = pages.getJSONObject(i);
page.put(Page.PAGE_EDITOR_TYPE, "tinyMCE");
pageRepository.update(page.getString(Keys.OBJECT_ID), page);
}
LOGGER.log(Level.FINEST, "Updated pages");
// Upgrades preference model // Upgrades preference model
final JSONObject preference = preferenceRepository.get(Preference.PREFERENCE); final JSONObject preference = preferenceRepository.get(Preference.PREFERENCE);
preference.put(Preference.COMMENTABLE, Preference.Default.DEFAULT_COMMENTABLE); preference.put(Preference.COMMENTABLE, Preference.Default.DEFAULT_COMMENTABLE);
preference.put(Preference.EDITOR_TYPE, Preference.Default.DEFAULT_EDITOR_TYPE); preference.put(Preference.EDITOR_TYPE, Preference.Default.DEFAULT_EDITOR_TYPE);
preference.put(Preference.VERSION, "0.4.5"); preference.put(Preference.VERSION, "0.4.6");
preferenceRepository.update(Preference.PREFERENCE, preference); preferenceRepository.update(Preference.PREFERENCE, preference);
...@@ -174,12 +145,12 @@ public final class UpgradeProcessor { ...@@ -174,12 +145,12 @@ public final class UpgradeProcessor {
} }
LOGGER.log(Level.SEVERE, "Upgrade failed.", e); LOGGER.log(Level.SEVERE, "Upgrade failed.", e);
throw new Exception("Upgrade failed from version 041 to version 045"); throw new Exception("Upgrade failed from version 045 to version 046");
} finally { } finally {
articleRepository.setCacheEnabled(true); articleRepository.setCacheEnabled(true);
} }
LOGGER.info("Upgraded from version 041 to version 045 successfully :-)"); LOGGER.info("Upgraded from version 045 to version 046 successfully :-)");
} }
/** /**
......
...@@ -35,13 +35,15 @@ import org.b3log.solo.service.PageQueryService; ...@@ -35,13 +35,15 @@ import org.b3log.solo.service.PageQueryService;
import org.b3log.solo.util.QueryResults; import org.b3log.solo.util.QueryResults;
import org.b3log.solo.util.Users; import org.b3log.solo.util.Users;
import org.b3log.latke.util.Requests; import org.b3log.latke.util.Requests;
import org.b3log.solo.model.Page;
import org.json.JSONArray;
import org.json.JSONObject; import org.json.JSONObject;
/** /**
* Plugin console request processing. * Plugin console request processing.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.0.0.0, Oct 27, 2011 * @version 1.0.0.1, Jun 20, 2012
* @since 0.4.0 * @since 0.4.0
*/ */
@RequestProcessor @RequestProcessor
...@@ -419,6 +421,19 @@ public final class PageConsole { ...@@ -419,6 +421,19 @@ public final class PageConsole {
final JSONObject requestJSONObject = Requests.buildPaginationRequest(path); final JSONObject requestJSONObject = Requests.buildPaginationRequest(path);
final JSONObject result = pageQueryService.getPages(requestJSONObject); final JSONObject result = pageQueryService.getPages(requestJSONObject);
final JSONArray pages = result.optJSONArray(Page.PAGES);
// Site-internal URLs process
for (int i = 0; i < pages.length(); i++) {
final JSONObject page = pages.getJSONObject(i);
if ("page".equals(page.optString(Page.PAGE_TYPE))) {
final String permalink = page.optString(Page.PAGE_PERMALINK);
page.put(Page.PAGE_PERMALINK, Latkes.getServePath() + permalink);
}
}
result.put(Keys.STATUS_CODE, true); result.put(Keys.STATUS_CODE, true);
renderer.setJSONObject(result); renderer.setJSONObject(result);
......
...@@ -41,7 +41,7 @@ import org.json.JSONObject; ...@@ -41,7 +41,7 @@ import org.json.JSONObject;
* Preference console request processing. * Preference console request processing.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.0.0.2, Mar 28, 2012 * @version 1.0.0.3, Jun 20, 2012
* @since 0.4.0 * @since 0.4.0
*/ */
@RequestProcessor @RequestProcessor
...@@ -241,13 +241,17 @@ public final class PreferenceConsole { ...@@ -241,13 +241,17 @@ public final class PreferenceConsole {
* { * {
* "sc": boolean, * "sc": boolean,
* "preference": { * "preference": {
* "recentArticleDisplayCount": int, * "mostViewArticleDisplayCount": int,
* "recentCommentDisplayCount": int,
* "mostUsedTagDisplayCount": int, * "mostUsedTagDisplayCount": int,
* "articleListDisplayCount": int, * "articleListDisplayCount": int,
* "articleListPaginationWindowSize": int, * "articleListPaginationWindowSize": int,
* "mostCommentArticleDisplayCount": int,
* "externalRelevantArticlesDisplayCount": int,
* "relevantArticlesDisplayCount": int,
* "randomArticlesDisplayCount": int,
* "blogTitle": "", * "blogTitle": "",
* "blogSubtitle": "", * "blogSubtitle": "",
* "mostCommentArticleDisplayCount": int,
* "blogHost": "", * "blogHost": "",
* "localeString": "", * "localeString": "",
* "timeZoneId": "", * "timeZoneId": "",
...@@ -259,9 +263,6 @@ public final class PreferenceConsole { ...@@ -259,9 +263,6 @@ public final class PreferenceConsole {
* }, ....]", * }, ....]",
* "noticeBoard": "", * "noticeBoard": "",
* "htmlHead": "", * "htmlHead": "",
* "externalRelevantArticlesDisplayCount": int,
* "relevantArticlesDisplayCount": int,
* "randomArticlesDisplayCount": int,
* "adminEmail": "", * "adminEmail": "",
* "metaKeywords": "", * "metaKeywords": "",
* "metaDescription": "", * "metaDescription": "",
...@@ -326,22 +327,23 @@ public final class PreferenceConsole { ...@@ -326,22 +327,23 @@ public final class PreferenceConsole {
* <pre> * <pre>
* { * {
* "preference": { * "preference": {
* "recentArticleDisplayCount": int, * "mostViewArticleDisplayCount": int,
* "recentCommentDisplayCount": int,
* "mostUsedTagDisplayCount": int, * "mostUsedTagDisplayCount": int,
* "articleListDisplayCount": int, * "articleListDisplayCount": int,
* "articleListPaginationWindowSize": int * "articleListPaginationWindowSize": int,
* "mostCommentArticleDisplayCount": int,
* "externalRelevantArticlesDisplayCount": int,
* "relevantArticlesDisplayCount": int,
* "randomArticlesDisplayCount": int,
* "blogTitle": "", * "blogTitle": "",
* "blogSubtitle": "", * "blogSubtitle": "",
* "mostCommentArticleDisplayCount": int,
* "skinDirName": "", * "skinDirName": "",
* "blogHost": "", * "blogHost": "",
* "localeString": "", * "localeString": "",
* "timeZoneId": "", * "timeZoneId": "",
* "noticeBoard": "", * "noticeBoard": "",
* "htmlHead": "", * "htmlHead": "",
* "externalRelevantArticlesDisplayCount": int,
* "relevantArticlesDisplayCount": int,
* "randomArticlesDisplayCount": int,
* "metaKeywords": "", * "metaKeywords": "",
* "metaDescription": "", * "metaDescription": "",
* "enableArticleUpdateHint": boolean, * "enableArticleUpdateHint": boolean,
...@@ -376,14 +378,17 @@ public final class PreferenceConsole { ...@@ -376,14 +378,17 @@ public final class PreferenceConsole {
final JSONObject preference = requestJSONObject.getJSONObject(Preference.PREFERENCE); final JSONObject preference = requestJSONObject.getJSONObject(Preference.PREFERENCE);
preferenceMgmtService.updatePreference(preference);
final JSONObject ret = new JSONObject(); final JSONObject ret = new JSONObject();
renderer.setJSONObject(ret);
if (isInvalid(preference, ret)) {
return;
}
preferenceMgmtService.updatePreference(preference);
ret.put(Keys.STATUS_CODE, true); ret.put(Keys.STATUS_CODE, true);
ret.put(Keys.MSG, langPropsService.get("updateSuccLabel")); ret.put(Keys.MSG, langPropsService.get("updateSuccLabel"));
renderer.setJSONObject(ret);
} catch (final ServiceException e) { } catch (final ServiceException e) {
LOGGER.log(Level.SEVERE, e.getMessage(), e); LOGGER.log(Level.SEVERE, e.getMessage(), e);
...@@ -392,4 +397,106 @@ public final class PreferenceConsole { ...@@ -392,4 +397,106 @@ public final class PreferenceConsole {
jsonObject.put(Keys.MSG, e.getMessage()); jsonObject.put(Keys.MSG, e.getMessage());
} }
} }
/**
* Checks whether the specified preference is invalid and sets the specified response object.
*
* @param preference the specified preference
* @param responseObject the specified response object
* @return {@code true} if the specified preference is invalid, returns {@code false} otherwise
*/
private boolean isInvalid(final JSONObject preference, final JSONObject responseObject) {
responseObject.put(Keys.STATUS_CODE, false);
final StringBuilder errMsgBuilder = new StringBuilder('[' + langPropsService.get("paramSettingsLabel"));
errMsgBuilder.append(" - ");
String input = preference.optString(Preference.EXTERNAL_RELEVANT_ARTICLES_DISPLAY_CNT);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("externalRelevantArticlesDisplayCntLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
input = preference.optString(Preference.RELEVANT_ARTICLES_DISPLAY_CNT);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("relevantArticlesDisplayCntLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
input = preference.optString(Preference.RANDOM_ARTICLES_DISPLAY_CNT);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("randomArticlesDisplayCntLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
input = preference.optString(Preference.MOST_COMMENT_ARTICLE_DISPLAY_CNT);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("indexMostCommentArticleDisplayCntLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
input = preference.optString(Preference.MOST_VIEW_ARTICLE_DISPLAY_CNT);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("indexMostViewArticleDisplayCntLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
input = preference.optString(Preference.RECENT_COMMENT_DISPLAY_CNT);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("indexRecentCommentDisplayCntLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
input = preference.optString(Preference.MOST_USED_TAG_DISPLAY_CNT);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("indexTagDisplayCntLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
input = preference.optString(Preference.ARTICLE_LIST_DISPLAY_COUNT);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("pageSizeLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
input = preference.optString(Preference.ARTICLE_LIST_PAGINATION_WINDOW_SIZE);
if (!isNonNegativeInteger(input)) {
errMsgBuilder.append(langPropsService.get("windowSizeLabel")).append("] ").append(langPropsService.get(
"nonNegativeIntegerOnlyLabel"));
responseObject.put(Keys.MSG, errMsgBuilder.toString());
return true;
}
return false;
}
/**
* Checks whether the specified input is a non-negative integer.
*
* @param input the specified input
* @return {@code true} if it is, returns {@code false} otherwise
*/
private boolean isNonNegativeInteger(final String input) {
try {
return 0 <= Integer.valueOf(input);
} catch (final Exception e) {
return false;
}
}
} }
...@@ -39,9 +39,7 @@ import org.b3log.latke.model.Pagination; ...@@ -39,9 +39,7 @@ import org.b3log.latke.model.Pagination;
import org.b3log.latke.model.Plugin; import org.b3log.latke.model.Plugin;
import org.b3log.latke.model.User; import org.b3log.latke.model.User;
import org.b3log.latke.plugin.ViewLoadEventData; import org.b3log.latke.plugin.ViewLoadEventData;
import org.b3log.latke.repository.FilterOperator; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.SortDirection;
import org.b3log.latke.service.ServiceException; import org.b3log.latke.service.ServiceException;
import org.b3log.latke.util.*; import org.b3log.latke.util.*;
import org.b3log.latke.util.freemarker.Templates; import org.b3log.latke.util.freemarker.Templates;
...@@ -154,7 +152,7 @@ public final class Filler { ...@@ -154,7 +152,7 @@ public final class Filler {
final int pageCount = (int) Math.ceil((double) publishedArticleCnt / (double) pageSize); final int pageCount = (int) Math.ceil((double) publishedArticleCnt / (double) pageSize);
final Query query = new Query().setCurrentPageNum(currentPageNum).setPageSize(pageSize).setPageCount(pageCount). final Query query = new Query().setCurrentPageNum(currentPageNum).setPageSize(pageSize).setPageCount(pageCount).
addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, PUBLISHED). setFilter(new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, PUBLISHED)).
addSort(Article.ARTICLE_PUT_TOP, SortDirection.DESCENDING). addSort(Article.ARTICLE_PUT_TOP, SortDirection.DESCENDING).
index(Article.ARTICLE_PERMALINK); index(Article.ARTICLE_PERMALINK);
......
...@@ -16,12 +16,8 @@ ...@@ -16,12 +16,8 @@
package org.b3log.solo.repository.impl; package org.b3log.solo.repository.impl;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.repository.AbstractRepository; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.Query;
import org.b3log.solo.model.Article; import org.b3log.solo.model.Article;
import org.b3log.latke.repository.RepositoryException;
import org.b3log.latke.repository.SortDirection;
import org.b3log.solo.model.ArchiveDate; import org.b3log.solo.model.ArchiveDate;
import org.b3log.solo.repository.ArchiveDateArticleRepository; import org.b3log.solo.repository.ArchiveDateArticleRepository;
import org.json.JSONArray; import org.json.JSONArray;
...@@ -45,8 +41,8 @@ public final class ArchiveDateArticleRepositoryImpl extends AbstractRepository i ...@@ -45,8 +41,8 @@ public final class ArchiveDateArticleRepositoryImpl extends AbstractRepository i
@Override @Override
public JSONObject getByArchiveDateId(final String archiveDateId, final int currentPageNum, final int pageSize) public JSONObject getByArchiveDateId(final String archiveDateId, final int currentPageNum, final int pageSize)
throws RepositoryException { throws RepositoryException {
final Query query = new Query().addFilter(ArchiveDate.ARCHIVE_DATE + "_" + Keys.OBJECT_ID, final Query query = new Query().setFilter(new PropertyFilter(ArchiveDate.ARCHIVE_DATE + "_" + Keys.OBJECT_ID,
FilterOperator.EQUAL, archiveDateId). FilterOperator.EQUAL, archiveDateId)).
addSort(Article.ARTICLE + "_" + Keys.OBJECT_ID, addSort(Article.ARTICLE + "_" + Keys.OBJECT_ID,
SortDirection.DESCENDING). SortDirection.DESCENDING).
setCurrentPageNum(currentPageNum). setCurrentPageNum(currentPageNum).
...@@ -59,7 +55,7 @@ public final class ArchiveDateArticleRepositoryImpl extends AbstractRepository i ...@@ -59,7 +55,7 @@ public final class ArchiveDateArticleRepositoryImpl extends AbstractRepository i
@Override @Override
public JSONObject getByArticleId(final String articleId) throws RepositoryException { public JSONObject getByArticleId(final String articleId) throws RepositoryException {
final Query query = new Query(); final Query query = new Query();
query.addFilter(Article.ARTICLE + "_" + Keys.OBJECT_ID, FilterOperator.EQUAL, articleId); query.setFilter(new PropertyFilter(Article.ARTICLE + "_" + Keys.OBJECT_ID, FilterOperator.EQUAL, articleId));
final JSONObject result = get(query); final JSONObject result = get(query);
final JSONArray array = result.optJSONArray(Keys.RESULTS); final JSONArray array = result.optJSONArray(Keys.RESULTS);
......
...@@ -21,11 +21,7 @@ import java.util.List; ...@@ -21,11 +21,7 @@ import java.util.List;
import java.util.logging.Level; import java.util.logging.Level;
import java.util.logging.Logger; import java.util.logging.Logger;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.repository.AbstractRepository; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.RepositoryException;
import org.b3log.latke.repository.SortDirection;
import org.b3log.latke.util.CollectionUtils; import org.b3log.latke.util.CollectionUtils;
import org.b3log.solo.model.ArchiveDate; import org.b3log.solo.model.ArchiveDate;
import org.b3log.solo.repository.ArchiveDateRepository; import org.b3log.solo.repository.ArchiveDateRepository;
...@@ -61,7 +57,7 @@ public final class ArchiveDateRepositoryImpl extends AbstractRepository implemen ...@@ -61,7 +57,7 @@ public final class ArchiveDateRepositoryImpl extends AbstractRepository implemen
} }
final Query query = new Query(); final Query query = new Query();
query.addFilter(ArchiveDate.ARCHIVE_TIME, FilterOperator.EQUAL, time).setPageCount(1); query.setFilter(new PropertyFilter(ArchiveDate.ARCHIVE_TIME, FilterOperator.EQUAL, time)).setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
final JSONArray array = result.optJSONArray(Keys.RESULTS); final JSONArray array = result.optJSONArray(Keys.RESULTS);
......
...@@ -54,8 +54,9 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -54,8 +54,9 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
@Override @Override
public JSONObject getByAuthorEmail(final String authorEmail, final int currentPageNum, final int pageSize) public JSONObject getByAuthorEmail(final String authorEmail, final int currentPageNum, final int pageSize)
throws RepositoryException { throws RepositoryException {
final Query query = new Query().addFilter(Article.ARTICLE_AUTHOR_EMAIL, FilterOperator.EQUAL, authorEmail). final Query query = new Query().setFilter(CompositeFilterOperator.and(
addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true). new PropertyFilter(Article.ARTICLE_AUTHOR_EMAIL, FilterOperator.EQUAL, authorEmail),
new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true))).
addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING). addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING).
setCurrentPageNum(currentPageNum).setPageSize(pageSize).setPageCount(1); setCurrentPageNum(currentPageNum).setPageSize(pageSize).setPageCount(1);
...@@ -64,7 +65,8 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -64,7 +65,8 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
@Override @Override
public JSONObject getByPermalink(final String permalink) throws RepositoryException { public JSONObject getByPermalink(final String permalink) throws RepositoryException {
final Query query = new Query().addFilter(Article.ARTICLE_PERMALINK, FilterOperator.EQUAL, permalink). final Query query = new Query().setFilter(
new PropertyFilter(Article.ARTICLE_PERMALINK, FilterOperator.EQUAL, permalink)).
setPageCount(1); setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
...@@ -80,7 +82,7 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -80,7 +82,7 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
@Override @Override
public List<JSONObject> getRecentArticles(final int fetchSize) throws RepositoryException { public List<JSONObject> getRecentArticles(final int fetchSize) throws RepositoryException {
final Query query = new Query(); final Query query = new Query();
query.addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true); query.setFilter(new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true));
query.addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING); query.addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING);
query.setCurrentPageNum(1); query.setCurrentPageNum(1);
query.setPageSize(fetchSize); query.setPageSize(fetchSize);
...@@ -96,7 +98,7 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -96,7 +98,7 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
public List<JSONObject> getMostCommentArticles(final int num) throws RepositoryException { public List<JSONObject> getMostCommentArticles(final int num) throws RepositoryException {
final Query query = new Query().addSort(Article.ARTICLE_COMMENT_COUNT, SortDirection.DESCENDING). final Query query = new Query().addSort(Article.ARTICLE_COMMENT_COUNT, SortDirection.DESCENDING).
addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING). addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING).
addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true). setFilter(new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true)).
setCurrentPageNum(1).setPageSize(num).setPageCount(1); setCurrentPageNum(1).setPageSize(num).setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
...@@ -110,7 +112,7 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -110,7 +112,7 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
final Query query = new Query(); final Query query = new Query();
query.addSort(Article.ARTICLE_VIEW_COUNT, SortDirection.DESCENDING). query.addSort(Article.ARTICLE_VIEW_COUNT, SortDirection.DESCENDING).
addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING); addSort(Article.ARTICLE_UPDATE_DATE, SortDirection.DESCENDING);
query.addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true); query.setFilter(new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true));
query.setCurrentPageNum(1); query.setCurrentPageNum(1);
query.setPageSize(num); query.setPageSize(num);
query.setPageCount(1); query.setPageCount(1);
...@@ -126,8 +128,10 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -126,8 +128,10 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
final JSONObject currentArticle = get(articleId); final JSONObject currentArticle = get(articleId);
final Date currentArticleCreateDate = (Date) currentArticle.opt(Article.ARTICLE_CREATE_DATE); final Date currentArticleCreateDate = (Date) currentArticle.opt(Article.ARTICLE_CREATE_DATE);
final Query query = new Query().addFilter(Article.ARTICLE_CREATE_DATE, FilterOperator.LESS_THAN, currentArticleCreateDate). final Query query = new Query().setFilter(
addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true). CompositeFilterOperator.and(
new PropertyFilter(Article.ARTICLE_CREATE_DATE, FilterOperator.LESS_THAN, currentArticleCreateDate),
new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true))).
addSort(Article.ARTICLE_CREATE_DATE, SortDirection.DESCENDING).setCurrentPageNum(1). addSort(Article.ARTICLE_CREATE_DATE, SortDirection.DESCENDING).setCurrentPageNum(1).
setPageSize(1).setPageCount(1). setPageSize(1).setPageCount(1).
addProjection(Article.ARTICLE_TITLE, String.class). addProjection(Article.ARTICLE_TITLE, String.class).
...@@ -158,8 +162,10 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -158,8 +162,10 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
final JSONObject currentArticle = get(articleId); final JSONObject currentArticle = get(articleId);
final Date currentArticleCreateDate = (Date) currentArticle.opt(Article.ARTICLE_CREATE_DATE); final Date currentArticleCreateDate = (Date) currentArticle.opt(Article.ARTICLE_CREATE_DATE);
final Query query = new Query().addFilter(Article.ARTICLE_CREATE_DATE, FilterOperator.GREATER_THAN, currentArticleCreateDate). final Query query = new Query().setFilter(
addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true). CompositeFilterOperator.and(
new PropertyFilter(Article.ARTICLE_CREATE_DATE, FilterOperator.GREATER_THAN, currentArticleCreateDate),
new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true))).
addSort(Article.ARTICLE_CREATE_DATE, SortDirection.ASCENDING).setCurrentPageNum(1). addSort(Article.ARTICLE_CREATE_DATE, SortDirection.ASCENDING).setCurrentPageNum(1).
setPageSize(1).setPageCount(1). setPageSize(1).setPageCount(1).
addProjection(Article.ARTICLE_TITLE, String.class). addProjection(Article.ARTICLE_TITLE, String.class).
...@@ -207,9 +213,10 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -207,9 +213,10 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
LOGGER.log(Level.FINEST, "Random mid[{0}]", mid); LOGGER.log(Level.FINEST, "Random mid[{0}]", mid);
Query query = new Query(); Query query = new Query();
query.addFilter(Article.ARTICLE_RANDOM_DOUBLE, FilterOperator.GREATER_THAN_OR_EQUAL, mid); query.setFilter(CompositeFilterOperator.and(
query.addFilter(Article.ARTICLE_RANDOM_DOUBLE, FilterOperator.LESS_THAN_OR_EQUAL, mid); new PropertyFilter(Article.ARTICLE_RANDOM_DOUBLE, FilterOperator.GREATER_THAN_OR_EQUAL, mid),
query.addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true); new PropertyFilter(Article.ARTICLE_RANDOM_DOUBLE, FilterOperator.LESS_THAN_OR_EQUAL, mid),
new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true)));
query.setCurrentPageNum(1); query.setCurrentPageNum(1);
query.setPageSize(fetchSize); query.setPageSize(fetchSize);
query.setPageCount(1); query.setPageCount(1);
...@@ -223,9 +230,10 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A ...@@ -223,9 +230,10 @@ public final class ArticleRepositoryImpl extends AbstractRepository implements A
final int reminingSize = fetchSize - array1.length(); final int reminingSize = fetchSize - array1.length();
if (0 != reminingSize) { // Query for remains if (0 != reminingSize) { // Query for remains
query = new Query(); query = new Query();
query.addFilter(Article.ARTICLE_RANDOM_DOUBLE, FilterOperator.GREATER_THAN_OR_EQUAL, 0D); query.setFilter(CompositeFilterOperator.and(
query.addFilter(Article.ARTICLE_RANDOM_DOUBLE, FilterOperator.LESS_THAN_OR_EQUAL, mid); new PropertyFilter(Article.ARTICLE_RANDOM_DOUBLE, FilterOperator.GREATER_THAN_OR_EQUAL, 0D),
query.addFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true); new PropertyFilter(Article.ARTICLE_RANDOM_DOUBLE, FilterOperator.LESS_THAN_OR_EQUAL, mid),
new PropertyFilter(Article.ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, true)));
query.setCurrentPageNum(1); query.setCurrentPageNum(1);
query.setPageSize(reminingSize); query.setPageSize(reminingSize);
query.setPageCount(1); query.setPageCount(1);
......
...@@ -22,11 +22,7 @@ import java.util.logging.Level; ...@@ -22,11 +22,7 @@ import java.util.logging.Level;
import java.util.logging.Logger; import java.util.logging.Logger;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.cache.Cache; import org.b3log.latke.cache.Cache;
import org.b3log.latke.repository.AbstractRepository; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.RepositoryException;
import org.b3log.latke.repository.SortDirection;
import org.b3log.solo.model.Comment; import org.b3log.solo.model.Comment;
import org.b3log.solo.repository.CommentRepository; import org.b3log.solo.repository.CommentRepository;
import org.b3log.latke.util.CollectionUtils; import org.b3log.latke.util.CollectionUtils;
...@@ -79,7 +75,7 @@ public final class CommentRepositoryImpl extends AbstractRepository implements C ...@@ -79,7 +75,7 @@ public final class CommentRepositoryImpl extends AbstractRepository implements C
public List<JSONObject> getComments(final String onId, final int currentPageNum, final int pageSize) public List<JSONObject> getComments(final String onId, final int currentPageNum, final int pageSize)
throws RepositoryException { throws RepositoryException {
final Query query = new Query().addSort(Keys.OBJECT_ID, SortDirection.DESCENDING). final Query query = new Query().addSort(Keys.OBJECT_ID, SortDirection.DESCENDING).
addFilter(Comment.COMMENT_ON_ID, FilterOperator.EQUAL, onId). setFilter(new PropertyFilter(Comment.COMMENT_ON_ID, FilterOperator.EQUAL, onId)).
setCurrentPageNum(currentPageNum). setCurrentPageNum(currentPageNum).
setPageSize(pageSize). setPageSize(pageSize).
setPageCount(1); setPageCount(1);
......
...@@ -17,11 +17,7 @@ package org.b3log.solo.repository.impl; ...@@ -17,11 +17,7 @@ package org.b3log.solo.repository.impl;
import java.util.logging.Logger; import java.util.logging.Logger;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.repository.AbstractRepository; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.RepositoryException;
import org.b3log.latke.repository.SortDirection;
import org.b3log.solo.model.Link; import org.b3log.solo.model.Link;
import org.b3log.solo.repository.LinkRepository; import org.b3log.solo.repository.LinkRepository;
import org.json.JSONArray; import org.json.JSONArray;
...@@ -47,7 +43,8 @@ public final class LinkRepositoryImpl extends AbstractRepository implements Link ...@@ -47,7 +43,8 @@ public final class LinkRepositoryImpl extends AbstractRepository implements Link
@Override @Override
public JSONObject getByAddress(final String address) throws RepositoryException { public JSONObject getByAddress(final String address) throws RepositoryException {
final Query query = new Query().addFilter(Link.LINK_ADDRESS, FilterOperator.EQUAL, address). final Query query = new Query().setFilter(
new PropertyFilter(Link.LINK_ADDRESS, FilterOperator.EQUAL, address)).
setPageCount(1); setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
...@@ -78,7 +75,7 @@ public final class LinkRepositoryImpl extends AbstractRepository implements Link ...@@ -78,7 +75,7 @@ public final class LinkRepositoryImpl extends AbstractRepository implements Link
@Override @Override
public JSONObject getByOrder(final int order) throws RepositoryException { public JSONObject getByOrder(final int order) throws RepositoryException {
final Query query = new Query(); final Query query = new Query();
query.addFilter(Link.LINK_ORDER, FilterOperator.EQUAL, order); query.setFilter(new PropertyFilter(Link.LINK_ORDER, FilterOperator.EQUAL, order));
final JSONObject result = get(query); final JSONObject result = get(query);
final JSONArray array = result.optJSONArray(Keys.RESULTS); final JSONArray array = result.optJSONArray(Keys.RESULTS);
...@@ -98,7 +95,8 @@ public final class LinkRepositoryImpl extends AbstractRepository implements Link ...@@ -98,7 +95,8 @@ public final class LinkRepositoryImpl extends AbstractRepository implements Link
} }
final Query query = new Query(); final Query query = new Query();
query.addFilter(Link.LINK_ORDER, FilterOperator.LESS_THAN, link.optInt(Link.LINK_ORDER)). query.setFilter(
new PropertyFilter(Link.LINK_ORDER, FilterOperator.LESS_THAN, link.optInt(Link.LINK_ORDER))).
addSort(Link.LINK_ORDER, SortDirection.DESCENDING); addSort(Link.LINK_ORDER, SortDirection.DESCENDING);
query.setCurrentPageNum(1); query.setCurrentPageNum(1);
query.setPageSize(1); query.setPageSize(1);
...@@ -121,7 +119,7 @@ public final class LinkRepositoryImpl extends AbstractRepository implements Link ...@@ -121,7 +119,7 @@ public final class LinkRepositoryImpl extends AbstractRepository implements Link
} }
final Query query = new Query(); final Query query = new Query();
query.addFilter(Link.LINK_ORDER, FilterOperator.GREATER_THAN, link.optInt(Link.LINK_ORDER)). query.setFilter(new PropertyFilter(Link.LINK_ORDER, FilterOperator.GREATER_THAN, link.optInt(Link.LINK_ORDER))).
addSort(Link.LINK_ORDER, SortDirection.ASCENDING); addSort(Link.LINK_ORDER, SortDirection.ASCENDING);
query.setCurrentPageNum(1); query.setCurrentPageNum(1);
query.setPageSize(1); query.setPageSize(1);
......
...@@ -18,11 +18,7 @@ package org.b3log.solo.repository.impl; ...@@ -18,11 +18,7 @@ package org.b3log.solo.repository.impl;
import java.util.List; import java.util.List;
import java.util.logging.Logger; import java.util.logging.Logger;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.repository.AbstractRepository; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.RepositoryException;
import org.b3log.latke.repository.SortDirection;
import org.b3log.latke.util.CollectionUtils; import org.b3log.latke.util.CollectionUtils;
import org.b3log.solo.model.Page; import org.b3log.solo.model.Page;
import org.b3log.solo.repository.PageRepository; import org.b3log.solo.repository.PageRepository;
...@@ -49,7 +45,8 @@ public final class PageRepositoryImpl extends AbstractRepository implements Page ...@@ -49,7 +45,8 @@ public final class PageRepositoryImpl extends AbstractRepository implements Page
@Override @Override
public JSONObject getByPermalink(final String permalink) throws RepositoryException { public JSONObject getByPermalink(final String permalink) throws RepositoryException {
final Query query = new Query().addFilter(Page.PAGE_PERMALINK, FilterOperator.EQUAL, permalink). final Query query = new Query().setFilter(
new PropertyFilter(Page.PAGE_PERMALINK, FilterOperator.EQUAL, permalink)).
setPageCount(1); setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
final JSONArray array = result.optJSONArray(Keys.RESULTS); final JSONArray array = result.optJSONArray(Keys.RESULTS);
...@@ -82,7 +79,8 @@ public final class PageRepositoryImpl extends AbstractRepository implements Page ...@@ -82,7 +79,8 @@ public final class PageRepositoryImpl extends AbstractRepository implements Page
return null; return null;
} }
final Query query = new Query().addFilter(Page.PAGE_ORDER, FilterOperator.LESS_THAN, page.optInt(Page.PAGE_ORDER)). final Query query = new Query().setFilter(
new PropertyFilter(Page.PAGE_ORDER, FilterOperator.LESS_THAN, page.optInt(Page.PAGE_ORDER))).
addSort(Page.PAGE_ORDER, SortDirection.DESCENDING). addSort(Page.PAGE_ORDER, SortDirection.DESCENDING).
setCurrentPageNum(1).setPageSize(1).setPageCount(1); setCurrentPageNum(1).setPageSize(1).setPageCount(1);
...@@ -103,7 +101,8 @@ public final class PageRepositoryImpl extends AbstractRepository implements Page ...@@ -103,7 +101,8 @@ public final class PageRepositoryImpl extends AbstractRepository implements Page
return null; return null;
} }
final Query query = new Query().addFilter(Page.PAGE_ORDER, FilterOperator.GREATER_THAN, page.optInt(Page.PAGE_ORDER)). final Query query = new Query().setFilter(
new PropertyFilter(Page.PAGE_ORDER, FilterOperator.GREATER_THAN, page.optInt(Page.PAGE_ORDER))).
addSort(Page.PAGE_ORDER, SortDirection.ASCENDING).setCurrentPageNum(1). addSort(Page.PAGE_ORDER, SortDirection.ASCENDING).setCurrentPageNum(1).
setPageSize(1). setPageSize(1).
setPageCount(1); setPageCount(1);
...@@ -120,7 +119,8 @@ public final class PageRepositoryImpl extends AbstractRepository implements Page ...@@ -120,7 +119,8 @@ public final class PageRepositoryImpl extends AbstractRepository implements Page
@Override @Override
public JSONObject getByOrder(final int order) throws RepositoryException { public JSONObject getByOrder(final int order) throws RepositoryException {
final Query query = new Query().addFilter(Page.PAGE_ORDER, FilterOperator.EQUAL, order). final Query query = new Query().setFilter(
new PropertyFilter(Page.PAGE_ORDER, FilterOperator.EQUAL, order)).
setPageCount(1); setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
final JSONArray array = result.optJSONArray(Keys.RESULTS); final JSONArray array = result.optJSONArray(Keys.RESULTS);
......
...@@ -21,11 +21,7 @@ import org.b3log.solo.model.Article; ...@@ -21,11 +21,7 @@ import org.b3log.solo.model.Article;
import org.b3log.solo.model.Tag; import org.b3log.solo.model.Tag;
import org.b3log.solo.repository.TagArticleRepository; import org.b3log.solo.repository.TagArticleRepository;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.repository.AbstractRepository; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.RepositoryException;
import org.b3log.latke.repository.SortDirection;
import org.b3log.latke.util.CollectionUtils; import org.b3log.latke.util.CollectionUtils;
import org.json.JSONArray; import org.json.JSONArray;
import org.json.JSONObject; import org.json.JSONObject;
...@@ -50,7 +46,8 @@ public final class TagArticleRepositoryImpl extends AbstractRepository implement ...@@ -50,7 +46,8 @@ public final class TagArticleRepositoryImpl extends AbstractRepository implement
@Override @Override
public List<JSONObject> getByArticleId(final String articleId) throws RepositoryException { public List<JSONObject> getByArticleId(final String articleId) throws RepositoryException {
final Query query = new Query().addFilter(Article.ARTICLE + "_" + Keys.OBJECT_ID, FilterOperator.EQUAL, articleId). final Query query = new Query().setFilter(
new PropertyFilter(Article.ARTICLE + "_" + Keys.OBJECT_ID, FilterOperator.EQUAL, articleId)).
setPageCount(1); setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
...@@ -62,7 +59,8 @@ public final class TagArticleRepositoryImpl extends AbstractRepository implement ...@@ -62,7 +59,8 @@ public final class TagArticleRepositoryImpl extends AbstractRepository implement
@Override @Override
public JSONObject getByTagId(final String tagId, final int currentPageNum, final int pageSize) public JSONObject getByTagId(final String tagId, final int currentPageNum, final int pageSize)
throws RepositoryException { throws RepositoryException {
final Query query = new Query().addFilter(Tag.TAG + "_" + Keys.OBJECT_ID, FilterOperator.EQUAL, tagId). final Query query = new Query().setFilter(
new PropertyFilter(Tag.TAG + "_" + Keys.OBJECT_ID, FilterOperator.EQUAL, tagId)).
addSort(Article.ARTICLE + "_" + Keys.OBJECT_ID, SortDirection.DESCENDING). addSort(Article.ARTICLE + "_" + Keys.OBJECT_ID, SortDirection.DESCENDING).
setCurrentPageNum(currentPageNum). setCurrentPageNum(currentPageNum).
setPageSize(pageSize). setPageSize(pageSize).
......
...@@ -21,11 +21,7 @@ import java.util.logging.Logger; ...@@ -21,11 +21,7 @@ import java.util.logging.Logger;
import org.b3log.solo.model.Tag; import org.b3log.solo.model.Tag;
import org.b3log.solo.repository.TagRepository; import org.b3log.solo.repository.TagRepository;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.repository.AbstractRepository; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.RepositoryException;
import org.b3log.latke.repository.SortDirection;
import org.b3log.latke.util.CollectionUtils; import org.b3log.latke.util.CollectionUtils;
import org.json.JSONArray; import org.json.JSONArray;
import org.json.JSONObject; import org.json.JSONObject;
...@@ -54,7 +50,8 @@ public final class TagRepositoryImpl extends AbstractRepository implements TagRe ...@@ -54,7 +50,8 @@ public final class TagRepositoryImpl extends AbstractRepository implements TagRe
@Override @Override
public JSONObject getByTitle(final String tagTitle) throws RepositoryException { public JSONObject getByTitle(final String tagTitle) throws RepositoryException {
final Query query = new Query().addFilter(Tag.TAG_TITLE, FilterOperator.EQUAL, tagTitle). final Query query = new Query().setFilter(
new PropertyFilter(Tag.TAG_TITLE, FilterOperator.EQUAL, tagTitle)).
setPageCount(1); setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
......
...@@ -19,10 +19,7 @@ import java.util.logging.Logger; ...@@ -19,10 +19,7 @@ import java.util.logging.Logger;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.model.Role; import org.b3log.latke.model.Role;
import org.b3log.latke.model.User; import org.b3log.latke.model.User;
import org.b3log.latke.repository.AbstractRepository; import org.b3log.latke.repository.*;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.RepositoryException;
import org.b3log.solo.repository.UserRepository; import org.b3log.solo.repository.UserRepository;
import org.json.JSONArray; import org.json.JSONArray;
import org.json.JSONObject; import org.json.JSONObject;
...@@ -48,7 +45,8 @@ public final class UserRepositoryImpl extends AbstractRepository implements User ...@@ -48,7 +45,8 @@ public final class UserRepositoryImpl extends AbstractRepository implements User
@Override @Override
public JSONObject getByEmail(final String email) throws RepositoryException { public JSONObject getByEmail(final String email) throws RepositoryException {
final Query query = new Query().setPageCount(1); final Query query = new Query().setPageCount(1);
query.addFilter(User.USER_EMAIL, FilterOperator.EQUAL, email.toLowerCase().trim()); query.setFilter(
new PropertyFilter(User.USER_EMAIL, FilterOperator.EQUAL, email.toLowerCase().trim()));
final JSONObject result = get(query); final JSONObject result = get(query);
final JSONArray array = result.optJSONArray(Keys.RESULTS); final JSONArray array = result.optJSONArray(Keys.RESULTS);
...@@ -62,7 +60,8 @@ public final class UserRepositoryImpl extends AbstractRepository implements User ...@@ -62,7 +60,8 @@ public final class UserRepositoryImpl extends AbstractRepository implements User
@Override @Override
public JSONObject getAdmin() throws RepositoryException { public JSONObject getAdmin() throws RepositoryException {
final Query query = new Query().addFilter(User.USER_ROLE, FilterOperator.EQUAL, Role.ADMIN_ROLE).setPageCount(1); final Query query = new Query().setFilter(
new PropertyFilter(User.USER_ROLE, FilterOperator.EQUAL, Role.ADMIN_ROLE)).setPageCount(1);
final JSONObject result = get(query); final JSONObject result = get(query);
final JSONArray array = result.optJSONArray(Keys.RESULTS); final JSONArray array = result.optJSONArray(Keys.RESULTS);
......
...@@ -35,7 +35,7 @@ import java.util.List; ...@@ -35,7 +35,7 @@ import java.util.List;
import java.util.logging.Level; import java.util.logging.Level;
import java.util.logging.Logger; import java.util.logging.Logger;
import org.b3log.latke.Keys; import org.b3log.latke.Keys;
import org.b3log.latke.repository.RepositoryException; import org.b3log.latke.repository.*;
import org.b3log.latke.service.ServiceException; import org.b3log.latke.service.ServiceException;
import org.b3log.latke.util.CollectionUtils; import org.b3log.latke.util.CollectionUtils;
import org.b3log.latke.util.Paginator; import org.b3log.latke.util.Paginator;
...@@ -258,7 +258,8 @@ public final class ArticleQueryService { ...@@ -258,7 +258,8 @@ public final class ArticleQueryService {
setPageSize(pageSize). setPageSize(pageSize).
addSort(ARTICLE_PUT_TOP, SortDirection.DESCENDING). addSort(ARTICLE_PUT_TOP, SortDirection.DESCENDING).
addSort(ARTICLE_CREATE_DATE, SortDirection.DESCENDING). addSort(ARTICLE_CREATE_DATE, SortDirection.DESCENDING).
addFilter(ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, articleIsPublished); setFilter(
new PropertyFilter(ARTICLE_IS_PUBLISHED, FilterOperator.EQUAL, articleIsPublished));
int articleCount = statistics.getBlogArticleCount(); int articleCount = statistics.getBlogArticleCount();
if (!articleIsPublished) { if (!articleIsPublished) {
...@@ -335,7 +336,8 @@ public final class ArticleQueryService { ...@@ -335,7 +336,8 @@ public final class ArticleQueryService {
final List<JSONObject> ret = new ArrayList<JSONObject>(); final List<JSONObject> ret = new ArrayList<JSONObject>();
final Query query = new Query().addFilter(Keys.OBJECT_ID, FilterOperator.IN, articleIds). final Query query = new Query().setFilter(
new PropertyFilter(Keys.OBJECT_ID, FilterOperator.IN, articleIds)).
setPageCount(1).index(Article.ARTICLE_PERMALINK); setPageCount(1).index(Article.ARTICLE_PERMALINK);
result = articleRepository.get(query); result = articleRepository.get(query);
final JSONArray articles = result.getJSONArray(Keys.RESULTS); final JSONArray articles = result.getJSONArray(Keys.RESULTS);
...@@ -389,7 +391,8 @@ public final class ArticleQueryService { ...@@ -389,7 +391,8 @@ public final class ArticleQueryService {
final List<JSONObject> ret = new ArrayList<JSONObject>(); final List<JSONObject> ret = new ArrayList<JSONObject>();
final Query query = new Query().addFilter(Keys.OBJECT_ID, FilterOperator.IN, articleIds). final Query query = new Query().setFilter(
new PropertyFilter(Keys.OBJECT_ID, FilterOperator.IN, articleIds)).
setPageCount(1).index(Article.ARTICLE_PERMALINK); setPageCount(1).index(Article.ARTICLE_PERMALINK);
result = articleRepository.get(query); result = articleRepository.get(query);
final JSONArray articles = result.getJSONArray(Keys.RESULTS); final JSONArray articles = result.getJSONArray(Keys.RESULTS);
......
...@@ -42,7 +42,7 @@ import org.json.JSONObject; ...@@ -42,7 +42,7 @@ import org.json.JSONObject;
* Page management service. * Page management service.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.0.0.6, Feb 25, 2012 * @version 1.0.0.7, Jun 8, 2012
* @since 0.4.0 * @since 0.4.0
*/ */
public final class PageMgmtService { public final class PageMgmtService {
...@@ -149,7 +149,7 @@ public final class PageMgmtService { ...@@ -149,7 +149,7 @@ public final class PageMgmtService {
// Editor type // Editor type
final JSONObject preference = preferenceQueryService.getPreference(); final JSONObject preference = preferenceQueryService.getPreference();
page.put(Page.PAGE_EDITOR_TYPE, preference.optString(Preference.EDITOR_TYPE)); newPage.put(Page.PAGE_EDITOR_TYPE, preference.optString(Preference.EDITOR_TYPE));
pageRepository.update(pageId, newPage); pageRepository.update(pageId, newPage);
......
...@@ -44,7 +44,7 @@ import org.json.JSONObject; ...@@ -44,7 +44,7 @@ import org.json.JSONObject;
* Skin utilities. * Skin utilities.
* *
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a> * @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.0.2.5, Jan 7, 2012 * @version 1.0.2.6, Jun 12, 2012
* @since 0.3.1 * @since 0.3.1
*/ */
public final class Skins { public final class Skins {
...@@ -56,8 +56,7 @@ public final class Skins { ...@@ -56,8 +56,7 @@ public final class Skins {
/** /**
* Properties map. * Properties map.
*/ */
private static final Map<String, Map<String, String>> LANG_MAP = private static final Map<String, Map<String, String>> LANG_MAP = new HashMap<String, Map<String, String>>();
new HashMap<String, Map<String, String>>();
/** /**
* Private default constructor. * Private default constructor.
...@@ -74,9 +73,7 @@ public final class Skins { ...@@ -74,9 +73,7 @@ public final class Skins {
* @param dataModel the specified data model * @param dataModel the specified data model
* @throws ServiceException service exception * @throws ServiceException service exception
*/ */
public static void fillSkinLangs(final String localeString, public static void fillSkinLangs(final String localeString, final String currentSkinDirName, final Map<String, Object> dataModel)
final String currentSkinDirName,
final Map<String, Object> dataModel)
throws ServiceException { throws ServiceException {
Stopwatchs.start("Fill Skin Langs"); Stopwatchs.start("Fill Skin Langs");
...@@ -86,8 +83,7 @@ public final class Skins { ...@@ -86,8 +83,7 @@ public final class Skins {
if (null == langs) { if (null == langs) {
LANG_MAP.clear(); // Collect unused skin languages LANG_MAP.clear(); // Collect unused skin languages
LOGGER.log(Level.INFO, LOGGER.log(Level.INFO, "Loading skin[dirName={0}, locale={1}]",
"Loading skin[dirName={0}, locale={1}]",
new Object[]{currentSkinDirName, localeString}); new Object[]{currentSkinDirName, localeString});
langs = new HashMap<String, String>(); langs = new HashMap<String, String>();
...@@ -97,25 +93,18 @@ public final class Skins { ...@@ -97,25 +93,18 @@ public final class Skins {
final String country = Locales.getCountry(localeString); final String country = Locales.getCountry(localeString);
final Properties props = new Properties(); final Properties props = new Properties();
props.load(new FileReader(webRootPath + "skins" props.load(new FileReader(webRootPath + "skins" + File.separator
+ File.separator + currentSkinDirName + File.separator
+ currentSkinDirName + Keys.LANGUAGE + File.separator + Keys.LANGUAGE + '_' + language
+ File.separator + '_' + country + ".properties"));
+ Keys.LANGUAGE + File.separator
+ Keys.LANGUAGE + '_' + language
+ '_'
+ country + ".properties"));
final Set<Object> keys = props.keySet(); final Set<Object> keys = props.keySet();
for (final Object key : keys) { for (final Object key : keys) {
langs.put((String) key, props.getProperty((String) key)); langs.put((String) key, props.getProperty((String) key));
} }
LANG_MAP.put(langName, langs); LANG_MAP.put(langName, langs);
LOGGER.log(Level.INFO, LOGGER.log(Level.INFO, "Loaded skin[dirName={0}, locale={1}, keyCount={2}]",
"Loaded skin[dirName={0}, locale={1}, keyCount={2}]", new Object[]{currentSkinDirName, localeString, langs.size()});
new Object[]{currentSkinDirName,
localeString,
langs.size()});
} }
dataModel.putAll(langs); dataModel.putAll(langs);
...@@ -151,9 +140,7 @@ public final class Skins { ...@@ -151,9 +140,7 @@ public final class Skins {
final JSONObject skin = new JSONObject(); final JSONObject skin = new JSONObject();
final String name = getSkinName(dirName); final String name = getSkinName(dirName);
if (null == name) { if (null == name) {
LOGGER.log(Level.WARNING, "The directory[{0}] does not" LOGGER.log(Level.WARNING, "The directory[{0}] does not contain any skin, ignored it", dirName);
+ "contain any skin, ignored it",
dirName);
continue; continue;
} }
...@@ -168,21 +155,17 @@ public final class Skins { ...@@ -168,21 +155,17 @@ public final class Skins {
LOGGER.log(Level.INFO, "Current skin[name={0}]", skinName); LOGGER.log(Level.INFO, "Current skin[name={0}]", skinName);
if (!skinDirNames.contains(currentSkinDirName)) { if (!skinDirNames.contains(currentSkinDirName)) {
LOGGER.log(Level.WARNING, LOGGER.log(Level.WARNING, "Configred skin[dirName={0}] can not find, try to use "
"Configred skin[dirName={0}] can not find, try to use " + "default skin[dirName=ease] instead.", currentSkinDirName);
+ "default skin[dirName=classic] instead.", if (!skinDirNames.contains("ease")) {
currentSkinDirName); LOGGER.log(Level.SEVERE, "Can not find skin[dirName=ease]");
if (!skinDirNames.contains("classic")) {
LOGGER.log(Level.SEVERE, "Can not find skin[dirName=classic]"); throw new IllegalStateException("Can not find default skin[dirName=ease], please redeploy your B3log Solo and make sure "
+ "contains this default skin!");
throw new IllegalStateException(
"Can not find default skin[dirName=classic], please "
+ "redeploy your B3log Solo and make sure contains this "
+ "default skin!");
} }
preference.put(SKIN_DIR_NAME, "classic"); preference.put(SKIN_DIR_NAME, "ease");
preference.put(SKIN_NAME, "经典淡蓝"); preference.put(SKIN_NAME, "ease");
PreferenceMgmtService.getInstance().updatePreference(preference); PreferenceMgmtService.getInstance().updatePreference(preference);
PageCaches.removeAll(); // Clears cache manually. PageCaches.removeAll(); // Clears cache manually.
...@@ -243,8 +226,9 @@ public final class Skins { ...@@ -243,8 +226,9 @@ public final class Skins {
* using the subdirectory of it as the skin directory name, for example, * using the subdirectory of it as the skin directory name, for example,
* <pre> * <pre>
* ${Web root}/skins/ * ${Web root}/skins/
* <b>default</b>/
* <b>mobile</b>/
* <b>classic</b>/ * <b>classic</b>/
* <b>simple-art</b>/
* </pre> * </pre>
* Skips files that name starts with . and {@linkplain File#isHidden() * Skips files that name starts with . and {@linkplain File#isHidden()
* hidden} files. * hidden} files.
......
<<<<<<< HEAD
/* /*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team * Copyright (c) 2009, 2010, 2011, 2012, B3log Team
* *
...@@ -100,3 +101,107 @@ public final class UserRepositoryImplTestCase extends AbstractTestCase { ...@@ -100,3 +101,107 @@ public final class UserRepositoryImplTestCase extends AbstractTestCase {
Assert.assertEquals(found.getString(User.USER_PASSWORD), "pass1"); Assert.assertEquals(found.getString(User.USER_PASSWORD), "pass1");
} }
} }
=======
/*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.b3log.solo.repository.impl;
import org.b3log.latke.Keys;
import org.b3log.latke.model.Role;
import org.b3log.latke.model.User;
import org.b3log.latke.repository.FilterOperator;
import org.b3log.latke.repository.PropertyFilter;
import org.b3log.latke.repository.Query;
import org.b3log.latke.repository.Transaction;
import org.b3log.solo.AbstractTestCase;
import org.b3log.solo.model.UserExt;
import org.b3log.solo.repository.UserRepository;
import org.json.JSONArray;
import org.json.JSONObject;
import org.testng.Assert;
import org.testng.annotations.Test;
/**
* {@link UserRepositoryImpl} test case.
*
* @author <a href="mailto:DL88250@gmail.com">Liang Ding</a>
* @version 1.0.0.1, Feb 21, 2012
*/
@Test(suiteName = "repository")
public final class UserRepositoryImplTestCase extends AbstractTestCase {
/**
* Tests.
*
* @throws Exception exception
*/
@Test
public void test() throws Exception {
final UserRepository userRepository = getUserRepository();
final JSONObject another = new JSONObject();
another.put(User.USER_NAME, "test1");
another.put(User.USER_EMAIL, "test1@gmail.com");
another.put(User.USER_PASSWORD, "pass1");
another.put(User.USER_ROLE, Role.DEFAULT_ROLE);
another.put(UserExt.USER_ARTICLE_COUNT, 0);
another.put(UserExt.USER_PUBLISHED_ARTICLE_COUNT, 0);
Transaction transaction = userRepository.beginTransaction();
userRepository.add(another);
transaction.commit();
Assert.assertNull(userRepository.getAdmin());
JSONObject admin = new JSONObject();
admin.put(User.USER_NAME, "test");
admin.put(User.USER_EMAIL, "test@gmail.com");
admin.put(User.USER_PASSWORD, "pass");
admin.put(User.USER_ROLE, Role.ADMIN_ROLE);
admin.put(UserExt.USER_ARTICLE_COUNT, 0);
admin.put(UserExt.USER_PUBLISHED_ARTICLE_COUNT, 0);
transaction = userRepository.beginTransaction();
userRepository.add(admin);
transaction.commit();
Assert.assertTrue(userRepository.isAdminEmail("test@gmail.com"));
Assert.assertFalse(userRepository.isAdminEmail("notFound@gmail.com"));
admin = userRepository.getAdmin();
Assert.assertNotNull(admin);
Assert.assertEquals("test", admin.optString(User.USER_NAME));
final JSONObject result =
userRepository.get(new Query().setFilter(
new PropertyFilter(User.USER_NAME, FilterOperator.EQUAL, "test1")));
final JSONArray users = result.getJSONArray(Keys.RESULTS);
Assert.assertEquals(users.length(), 1);
Assert.assertEquals(users.getJSONObject(0).getString(User.USER_EMAIL),
"test1@gmail.com");
final JSONObject notFound =
userRepository.getByEmail("not.found@gmail.com");
Assert.assertNull(notFound);
final JSONObject found = userRepository.getByEmail("test1@gmail.com");
Assert.assertNotNull(found);
Assert.assertEquals(found.getString(User.USER_PASSWORD), "pass1");
}
}
>>>>>>> origin/0.4.6
# #
# Copyright (C) 2009, 2010, 2010, B3log Team # Copyright (C) 2009, 2010, 2011, B3log Team
# #
# Licensed under the Apache License, Version 2.0 (the "License"); # Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License. # you may not use this file except in compliance with the License.
...@@ -15,13 +15,12 @@ ...@@ -15,13 +15,12 @@
# #
# #
# Description: Classic blue skin. # Description: ease skin (mock for test).
# Version: 1.0.0.6, May 7, 2012 # Version: 1.0.0.0, Jun 27, 2012
# Author: Liang Ding # Author: Liang Ding
# Author: Liyuan Li
# #
name=\u7ecf\u5178\u6de1\u84dd name=ease
version=2.0.3 version=1.0.1
forSolo=0.4.5 forSolo=0.4.6
memo=\u8fd9\u4e2a\u76ae\u80a4\u5f88\u4e11\u4e48\uff1f\u6211\u52d2\u4e2a\u53bb\u3002 memo=\u56de\u5f52\u606c\u9759
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<!-- <!--
Description: B3log Solo parent POM. Description: B3log Solo parent POM.
Version: 2.0.1.9, May 29, 2012 Version: 2.0.2.1, Jun 27, 2012
Author: Liang Ding Author: Liang Ding
--> -->
<project xmlns="http://maven.apache.org/POM/4.0.0" <project xmlns="http://maven.apache.org/POM/4.0.0"
...@@ -11,7 +11,7 @@ ...@@ -11,7 +11,7 @@
<groupId>org.b3log</groupId> <groupId>org.b3log</groupId>
<artifactId>solo</artifactId> <artifactId>solo</artifactId>
<packaging>pom</packaging> <packaging>pom</packaging>
<version>0.4.5</version> <version>0.4.6</version>
<name>B3log Solo</name> <name>B3log Solo</name>
<url>https://github.com/b3log/b3log-solo</url> <url>https://github.com/b3log/b3log-solo</url>
<description> <description>
...@@ -28,13 +28,13 @@ ...@@ -28,13 +28,13 @@
<!-- Properties --> <!-- Properties -->
<properties> <properties>
<servlet.version>2.5</servlet.version> <servlet.version>2.5</servlet.version>
<org.b3log.solo.version>0.4.5</org.b3log.solo.version> <org.b3log.solo.version>0.4.6</org.b3log.solo.version>
<org.b3log.latke.version>0.5.0-SNAPSHOT</org.b3log.latke.version> <org.b3log.latke.version>0.5.0-SNAPSHOT</org.b3log.latke.version>
<org.b3log.latke-gae.version>0.5.0-SNAPSHOT</org.b3log.latke-gae.version> <org.b3log.latke-gae.version>0.5.0-SNAPSHOT</org.b3log.latke-gae.version>
<org.b3log.latke-repository-mysql.version>0.5.0-SNAPSHOT</org.b3log.latke-repository-mysql.version> <org.b3log.latke-repository-mysql.version>0.5.0-SNAPSHOT</org.b3log.latke-repository-mysql.version>
<gae.version>1.6.5</gae.version> <gae.version>1.7.0</gae.version>
<freemarker-gae.version>2.3.18</freemarker-gae.version> <freemarker-gae.version>2.3.19</freemarker-gae.version>
<jsoup.version>1.5.2</jsoup.version> <jsoup.version>1.5.2</jsoup.version>
<markdownpapers-core.version>1.2.7</markdownpapers-core.version> <markdownpapers-core.version>1.2.7</markdownpapers-core.version>
<!-- <com.google.api.client.version>1.2.1-alpha</com.google.api.client.version>--> <!-- <com.google.api.client.version>1.2.1-alpha</com.google.api.client.version>-->
......
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<!-- <!--
Description: B3log Solo GAE POM. Description: B3log Solo GAE POM.
Version: 2.0.0.6, May 11, 2012 Version: 2.0.0.7, Jun 19, 2012
Author: Liang Ding Author: Liang Ding
--> -->
<project xmlns="http://maven.apache.org/POM/4.0.0" <project xmlns="http://maven.apache.org/POM/4.0.0"
...@@ -19,7 +19,7 @@ ...@@ -19,7 +19,7 @@
<parent> <parent>
<groupId>org.b3log</groupId> <groupId>org.b3log</groupId>
<artifactId>solo-war</artifactId> <artifactId>solo-war</artifactId>
<version>0.4.5</version> <version>0.4.6</version>
</parent> </parent>
<properties> <properties>
......
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<!-- <!--
Description: B3log Solo (MySQL) standard Servlet container POM. Description: B3log Solo (MySQL) standard Servlet container POM.
Version: 1.0.0.2, May 11, 2012 Version: 1.0.0.3, Jun 19, 2012
Author: Liang Ding Author: Liang Ding
--> -->
<project xmlns="http://maven.apache.org/POM/4.0.0" <project xmlns="http://maven.apache.org/POM/4.0.0"
...@@ -19,7 +19,7 @@ ...@@ -19,7 +19,7 @@
<parent> <parent>
<groupId>org.b3log</groupId> <groupId>org.b3log</groupId>
<artifactId>solo-war</artifactId> <artifactId>solo-war</artifactId>
<version>0.4.5</version> <version>0.4.6</version>
</parent> </parent>
<properties> <properties>
......
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<!-- <!--
Description: B3log Solo WAR POM. Description: B3log Solo WAR POM.
Version: 2.0.1.0, May 29, 2012 Version: 2.0.1.1, Jun 19, 2012
Author: Liang Ding Author: Liang Ding
--> -->
<project xmlns="http://maven.apache.org/POM/4.0.0" <project xmlns="http://maven.apache.org/POM/4.0.0"
...@@ -19,7 +19,7 @@ ...@@ -19,7 +19,7 @@
<parent> <parent>
<groupId>org.b3log</groupId> <groupId>org.b3log</groupId>
<artifactId>solo</artifactId> <artifactId>solo</artifactId>
<version>0.4.5</version> <version>0.4.6</version>
</parent> </parent>
<modules> <modules>
......
...@@ -16,7 +16,7 @@ ...@@ -16,7 +16,7 @@
# #
# Description: B3log Solo language configurations(en_US). # Description: B3log Solo language configurations(en_US).
# Version: 2.0.9.2, May 22, 2012 # Version: 2.0.9.3, Jun 20, 2012
# Author: Liang Ding # Author: Liang Ding
# Author: Liyuan Li # Author: Liyuan Li
# #
...@@ -184,15 +184,25 @@ categoryLabel=Category ...@@ -184,15 +184,25 @@ categoryLabel=Category
noticeBoard1Label=Notice Board: noticeBoard1Label=Notice Board:
noticeBoardLabel=Notice Board noticeBoardLabel=Notice Board
htmlhead1Label=HTML head: htmlhead1Label=HTML head:
indexTagDisplayCntLabel=Index Tag Display Count
indexTagDisplayCnt1Label=Index Tag Display Count: indexTagDisplayCnt1Label=Index Tag Display Count:
indexRecentArticleDisplayCntLabel=Recent Article Display Count
indexRecentArticleDisplayCnt1Label=Recent Article Display Count: indexRecentArticleDisplayCnt1Label=Recent Article Display Count:
indexRecentCommentDisplayCntLabel=Recent Comment Display Count
indexRecentCommentDisplayCnt1Label=Recent Comment Display Count: indexRecentCommentDisplayCnt1Label=Recent Comment Display Count:
indexMostCommentArticleDisplayCntLabel=Most Comment Article Display Count
indexMostCommentArticleDisplayCnt1Label=Most Comment Article Display Count: indexMostCommentArticleDisplayCnt1Label=Most Comment Article Display Count:
indexMostViewArticleDisplayCntLabel=Most View Article Display Count
indexMostViewArticleDisplayCnt1Label=Most View Article Display Count: indexMostViewArticleDisplayCnt1Label=Most View Article Display Count:
relevantArticlesDisplayCntLabel=Relevant Article Display Count
relevantArticlesDisplayCnt1Label=Relevant Article Display Count: relevantArticlesDisplayCnt1Label=Relevant Article Display Count:
randomArticlesDisplayCntLabel=Random Article Display Count
randomArticlesDisplayCnt1Label=Random Article Display Count: randomArticlesDisplayCnt1Label=Random Article Display Count:
externalRelevantArticlesDisplayCntLabel=External Relevant Article Display Count
externalRelevantArticlesDisplayCnt1Label=External Relevant Article Display Count: externalRelevantArticlesDisplayCnt1Label=External Relevant Article Display Count:
windowSizeLabel=Pagination Window Size
windowSize1Label=Pagination Window Size: windowSize1Label=Pagination Window Size:
pageSizeLabel=Pagination Page Size
pageSize1Label=Pagination Page Size: pageSize1Label=Pagination Page Size:
blogTitle1Label=Blog Title: blogTitle1Label=Blog Title:
blogSubtitle1Label=Blog Subtitle: blogSubtitle1Label=Blog Subtitle:
...@@ -298,6 +308,7 @@ nameTooLongLabel=Sorry, your username must be between 2 and 20 characters long. ...@@ -298,6 +308,7 @@ nameTooLongLabel=Sorry, your username must be between 2 and 20 characters long.
mailCannotEmptyLabel=Mail is empty mailCannotEmptyLabel=Mail is empty
mailInvalidLabel=Mail is invalid mailInvalidLabel=Mail is invalid
urlInvalidLabel=URL is invalid urlInvalidLabel=URL is invalid
nonNegativeIntegerOnlyLabel=Non-Negative integer only
commentContentCannotEmptyLabel=Sorry, your content must be between 2 and 500 characters long. commentContentCannotEmptyLabel=Sorry, your content must be between 2 and 500 characters long.
captchaCannotEmptyLabel=Captcha is empty captchaCannotEmptyLabel=Captcha is empty
loadingLabel=Loading.... loadingLabel=Loading....
......
...@@ -16,7 +16,7 @@ ...@@ -16,7 +16,7 @@
# #
# Description: B3log Solo default language configurations(zh_CN). # Description: B3log Solo default language configurations(zh_CN).
# Version: 2.0.9.8, May 22, 2012 # Version: 2.0.9.9, Jun 20, 2012
# Author: Liang Ding # Author: Liang Ding
# Author: Liyuan Li # Author: Liyuan Li
# #
...@@ -184,15 +184,25 @@ categoryLabel=\u5206\u7c7b ...@@ -184,15 +184,25 @@ categoryLabel=\u5206\u7c7b
noticeBoard1Label=\u516c\u544a\uff1a noticeBoard1Label=\u516c\u544a\uff1a
noticeBoardLabel=\u516c\u544a noticeBoardLabel=\u516c\u544a
htmlhead1Label=HTML head\uff1a htmlhead1Label=HTML head\uff1a
indexTagDisplayCnt1Label= \u9996\u9875\u6807\u7b7e\u663e\u793a\u6570\uff1a indexTagDisplayCntLabel=\u9996\u9875\u6807\u7b7e\u663e\u793a\u6570
indexTagDisplayCnt1Label=\u9996\u9875\u6807\u7b7e\u663e\u793a\u6570\uff1a
indexRecentArticleDisplayCntLabel=\u6700\u65b0\u6587\u7ae0\u663e\u793a\u6570\u76ee
indexRecentArticleDisplayCnt1Label=\u6700\u65b0\u6587\u7ae0\u663e\u793a\u6570\u76ee\uff1a indexRecentArticleDisplayCnt1Label=\u6700\u65b0\u6587\u7ae0\u663e\u793a\u6570\u76ee\uff1a
indexRecentCommentDisplayCntLabel=\u6700\u65b0\u8bc4\u8bba\u663e\u793a\u6570\u76ee
indexRecentCommentDisplayCnt1Label=\u6700\u65b0\u8bc4\u8bba\u663e\u793a\u6570\u76ee\uff1a indexRecentCommentDisplayCnt1Label=\u6700\u65b0\u8bc4\u8bba\u663e\u793a\u6570\u76ee\uff1a
indexMostCommentArticleDisplayCntLabel=\u8bc4\u8bba\u6700\u591a\u6587\u7ae0\u663e\u793a\u6570\u76ee
indexMostCommentArticleDisplayCnt1Label=\u8bc4\u8bba\u6700\u591a\u6587\u7ae0\u663e\u793a\u6570\u76ee\uff1a indexMostCommentArticleDisplayCnt1Label=\u8bc4\u8bba\u6700\u591a\u6587\u7ae0\u663e\u793a\u6570\u76ee\uff1a
indexMostViewArticleDisplayCnt1Label=\u8bbf\u95ee\u6700\u591a\u6700\u591a\u6587\u7ae0\u663e\u793a\u6570\u76ee\uff1a indexMostViewArticleDisplayCntLabel=\u8bbf\u95ee\u6700\u591a\u6587\u7ae0\u663e\u793a\u6570\u76ee
indexMostViewArticleDisplayCnt1Label=\u8bbf\u95ee\u6700\u591a\u6587\u7ae0\u663e\u793a\u6570\u76ee\uff1a
relevantArticlesDisplayCntLabel=\u76f8\u5173\u9605\u8bfb\u663e\u793a\u6570\u76ee
relevantArticlesDisplayCnt1Label=\u76f8\u5173\u9605\u8bfb\u663e\u793a\u6570\u76ee\uff1a relevantArticlesDisplayCnt1Label=\u76f8\u5173\u9605\u8bfb\u663e\u793a\u6570\u76ee\uff1a
randomArticlesDisplayCntLabel=\u968f\u673a\u9605\u8bfb\u663e\u793a\u6570\u76ee
randomArticlesDisplayCnt1Label=\u968f\u673a\u9605\u8bfb\u663e\u793a\u6570\u76ee\uff1a randomArticlesDisplayCnt1Label=\u968f\u673a\u9605\u8bfb\u663e\u793a\u6570\u76ee\uff1a
externalRelevantArticlesDisplayCntLabel=\u7ad9\u5916\u76f8\u5173\u9605\u8bfb\u663e\u793a\u6570\u76ee
externalRelevantArticlesDisplayCnt1Label=\u7ad9\u5916\u76f8\u5173\u9605\u8bfb\u663e\u793a\u6570\u76ee\uff1a externalRelevantArticlesDisplayCnt1Label=\u7ad9\u5916\u76f8\u5173\u9605\u8bfb\u663e\u793a\u6570\u76ee\uff1a
windowSizeLabel=\u5206\u9875\u9875\u7801\u6700\u5927\u5bbd\u5ea6
windowSize1Label=\u5206\u9875\u9875\u7801\u6700\u5927\u5bbd\u5ea6\uff1a windowSize1Label=\u5206\u9875\u9875\u7801\u6700\u5927\u5bbd\u5ea6\uff1a
pageSizeLabel=\u5206\u9875\u6bcf\u9875\u663e\u793a\u6587\u7ae0\u6570
pageSize1Label=\u5206\u9875\u6bcf\u9875\u663e\u793a\u6587\u7ae0\u6570\uff1a pageSize1Label=\u5206\u9875\u6bcf\u9875\u663e\u793a\u6587\u7ae0\u6570\uff1a
blogTitle1Label=\u535a\u5ba2\u6807\u9898\uff1a blogTitle1Label=\u535a\u5ba2\u6807\u9898\uff1a
blogSubtitle1Label=\u535a\u5ba2\u5b50\u6807\u9898\uff1a blogSubtitle1Label=\u535a\u5ba2\u5b50\u6807\u9898\uff1a
...@@ -298,6 +308,7 @@ nameTooLongLabel=\u59d3\u540d\u53ea\u80fd\u4e3a 2 \u5230 20 \u4e2a\u5b57\u7b26\u ...@@ -298,6 +308,7 @@ nameTooLongLabel=\u59d3\u540d\u53ea\u80fd\u4e3a 2 \u5230 20 \u4e2a\u5b57\u7b26\u
mailCannotEmptyLabel=\u90ae\u7bb1\u4e0d\u80fd\u4e3a\u7a7a\uff01 mailCannotEmptyLabel=\u90ae\u7bb1\u4e0d\u80fd\u4e3a\u7a7a\uff01
mailInvalidLabel=\u90ae\u7bb1\u683c\u5f0f\u4e0d\u6b63\u786e\uff01 mailInvalidLabel=\u90ae\u7bb1\u683c\u5f0f\u4e0d\u6b63\u786e\uff01
urlInvalidLabel=\u94fe\u63a5\u683c\u5f0f\u4e0d\u6b63\u786e\uff01 urlInvalidLabel=\u94fe\u63a5\u683c\u5f0f\u4e0d\u6b63\u786e\uff01
nonNegativeIntegerOnlyLabel=\u53ea\u80fd\u4e3a\u975e\u8d1f\u6574\u6570\uff01
commentContentCannotEmptyLabel=\u8bc4\u8bba\u5185\u5bb9\u53ea\u80fd\u4e3a 2 \u5230 500 \u4e2a\u5b57\u7b26\uff01 commentContentCannotEmptyLabel=\u8bc4\u8bba\u5185\u5bb9\u53ea\u80fd\u4e3a 2 \u5230 500 \u4e2a\u5b57\u7b26\uff01
captchaCannotEmptyLabel=\u9a8c\u8bc1\u7801\u4e0d\u80fd\u4e3a\u7a7a\uff01 captchaCannotEmptyLabel=\u9a8c\u8bc1\u7801\u4e0d\u80fd\u4e3a\u7a7a\uff01
loadingLabel=\u8f7d\u5165\u4e2d.... loadingLabel=\u8f7d\u5165\u4e2d....
......
...@@ -47,4 +47,4 @@ cache=GAE ...@@ -47,4 +47,4 @@ cache=GAE
userService=LOCAL userService=LOCAL
#### Static resource version #### #### Static resource version ####
staticResourceVersion=201205021456 staticResourceVersion=201206280945
\ No newline at end of file \ No newline at end of file
This diff is collapsed.
...@@ -4,16 +4,16 @@ Project home: https://github.com/b3log/b3log-solo ...@@ -4,16 +4,16 @@ Project home: https://github.com/b3log/b3log-solo
Request features/Report bugs: https://github.com/b3log/b3log-solo/issues/new Request features/Report bugs: https://github.com/b3log/b3log-solo/issues/new
* QQ Qun: 13139268 * QQ Qun: 13139268
* User Guide: http://code.google.com/p/b3log-solo/wiki/UserGuide * User Guide: https://github.com/b3log/b3log-solo/wiki/Pre_installation
* Dev Guide: http://code.google.com/p/b3log-solo/wiki/pre_dev * Dev Guide: https://github.com/b3log/b3log-solo/wiki/Pre_dev
* Skin Dev Guide: http://code.google.com/p/b3log-solo/wiki/develop_steps * Skin Dev Guide: https://github.com/b3log/b3log-solo/wiki/Develop_steps
* Plugin Dev Guide: https://docs.google.com/document/pub?id=15H7Q3EBo-44v61Xp_epiYY7vK_gPJLkQaT7T1gkE64w&pli=1 * Plugin Dev Guide: https://docs.google.com/document/pub?id=15H7Q3EBo-44v61Xp_epiYY7vK_gPJLkQaT7T1gkE64w&pli=1
==== ====
B3log Index: http://b3log.org B3log Index: http://b3log.org
B3log Team: http://code.google.com/p/b3log-solo/wiki/about_us B3log Team: https://github.com/b3log/b3log-solo/wiki/About_us
Join B3log Team: http://code.google.com/p/b3log-solo/wiki/join_us Join B3log Team: https://github.com/b3log/b3log-solo/wiki/Join_us
==== ====
平等,自由,奔放 平等,自由,奔放
......
...@@ -20,12 +20,12 @@ ...@@ -20,12 +20,12 @@
Description: Web deployment descriptor on GAE. See Description: Web deployment descriptor on GAE. See
http://code.google.com/intl/en/appengine/docs/java/config/appconfig.html http://code.google.com/intl/en/appengine/docs/java/config/appconfig.html
for more details. for more details.
Version: 1.0.3.5, May 18, 2012 Version: 1.0.3.7, Jun 19, 2012
Author: Liang Ding Author: Liang Ding
--> -->
<appengine-web-app xmlns="http://appengine.google.com/ns/1.0"> <appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
<application>solo-demo</application> <application>solo-demo</application>
<version>045</version> <version>046</version>
<sessions-enabled>true</sessions-enabled> <sessions-enabled>true</sessions-enabled>
...@@ -41,7 +41,6 @@ ...@@ -41,7 +41,6 @@
<include path="/favicon.ico" /> <include path="/favicon.ico" />
<include path="/favicon.png" /> <include path="/favicon.png" />
<include path="/robots.txt" /> <include path="/robots.txt" />
<include path="/error/*.html" />
<include path="/js/**.js" /> <include path="/js/**.js" />
<include path="/js/**/*.js" /> <include path="/js/**/*.js" />
......
...@@ -21,8 +21,8 @@ ...@@ -21,8 +21,8 @@
</#if> </#if>
</head> </head>
<body onhashchange="admin.setCurByHash();"> <body onhashchange="admin.setCurByHash();">
<div id="loadMsg">${loadingLabel}</div> <div class="tip"><span id="loadMsg">${loadingLabel}</span></div>
<div id="tipMsg"></div> <div class="tip tip-msg"><span id="tipMsg"></span></div>
<div id="allPanel"> <div id="allPanel">
<div id="top"> <div id="top">
<a href="http://b3log.org" target="_blank" class="hover"> <a href="http://b3log.org" target="_blank" class="hover">
......
...@@ -4,6 +4,7 @@ ...@@ -4,6 +4,7 @@
"servePath": "${servePath}" "servePath": "${servePath}"
}; };
var Label = { var Label = {
"skinDirName": "ease",
"editorType": "${editorType}", "editorType": "${editorType}",
"userRole": "${userRole}", "userRole": "${userRole}",
"PAGE_SIZE": "${articleListDisplayCount}", "PAGE_SIZE": "${articleListDisplayCount}",
...@@ -81,7 +82,34 @@ ...@@ -81,7 +82,34 @@
"linkEmptyLabel": "${linkEmptyLabel}", "linkEmptyLabel": "${linkEmptyLabel}",
"openMethodLabel": "${openMethodLabel}", "openMethodLabel": "${openMethodLabel}",
"typeLabel": "${typeLabel}", "typeLabel": "${typeLabel}",
"markdownHelpLabel": "${markdownHelpLabel}" "markdownHelpLabel": "${markdownHelpLabel}",
"notFoundLabel": "${notFoundLabel}",
"em00Label": "${em00Label}",
"em01Label": "${em01Label}",
"em02Label": "${em02Label}",
"em03Label": "${em03Label}",
"em04Label": "${em04Label}",
"em05Label": "${em05Label}",
"em06Label": "${em06Label}",
"em07Label": "${em07Label}",
"em08Label": "${em08Label}",
"em09Label": "${em09Label}",
"em10Label": "${em10Label}",
"em11Label": "${em11Label}",
"em12Label": "${em12Label}",
"em13Label": "${em13Label}",
"em14Label": "${em14Label}",
"paramSettingsLabel": "${paramSettingsLabel}",
"nonNegativeIntegerOnlyLabel": "${nonNegativeIntegerOnlyLabel}",
"indexTagDisplayCntLabel": "${indexTagDisplayCntLabel}",
"indexRecentCommentDisplayCntLabel": "${indexRecentCommentDisplayCntLabel}",
"indexMostCommentArticleDisplayCntLabel": "${indexMostCommentArticleDisplayCntLabel}",
"indexMostViewArticleDisplayCntLabel": "${indexMostViewArticleDisplayCntLabel}",
"pageSizeLabel": "${pageSizeLabel}",
"windowSizeLabel": "${windowSizeLabel}",
"randomArticlesDisplayCntLabel": "${randomArticlesDisplayCntLabel}",
"relevantArticlesDisplayCntLabel": "${relevantArticlesDisplayCntLabel}",
"externalRelevantArticlesDisplayCntLabel": "${externalRelevantArticlesDisplayCntLabel}"
}; };
admin.init(); admin.init();
......
This diff is collapsed.
<<<<<<< HEAD
/** /**
* base style * base style
* *
...@@ -500,4 +501,524 @@ button:hover,.button:hover { ...@@ -500,4 +501,524 @@ button:hover,.button:hover {
#captcha, #captchaReply { #captcha, #captchaReply {
cursor: pointer; cursor: pointer;
} }
=======
/*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* base style
*
* @author <a href="mailto:LLY219@gmail.com">Liyuan Li</a>
* @version 1.0.2.1, Mar 28, 2012
*/
html, body, div, ul, li, h1, h2, h3, h4, h5, h6, p, dd, dl, ol {
margin: 0;
padding: 0;
}
body {
background-color: #FFF;
color: #000;
font-family: Helvetica,Arial,sans-serif,\5fae\8f6f\96c5\9ed1;
font-size: small;
}
img {
border: medium none;
margin: 0;
padding: 0;
vertical-align: middle;
}
h1 {
font-size: 160%;
}
h2 {
font-size: 140%;
}
h3 {
font-size: 120%;
}
h4 {
font-size: 110%;
}
textarea {
overflow: auto;
}
li {
margin-left: 12px;
}
button, .button {
background: url(../images/icon.png) repeat center bottom;
border: 1px solid;
border-color: #CCC #BBBBBB #A0A0A0;
border-radius: 4px;
height: 28px;
margin: 0;
padding: 0 6px;
vertical-align: top;
}
button:hover,.button:hover {
border-color: #BBB;
}
.padding12 {
padding: 12px;
}
.paddingBottom12 {
padding-bottom: 12px !important;
}
.paddingTop12 {
padding-top: 12px !important;
}
.margin12 {
margin: 12px;
}
.marginTop12 {
margin-top: 12px !important;
}
.marginBottom12 {
margin-bottom: 12px !important;
}
.marginLeft12 {
margin-left: 12px !important;;
}
.marginLeft6 {
margin-left: 6px !important;;
}
.marginRight12 {
margin-right: 12px !important;;
}
.f-bold {
font-weight: bold !important;
}
.nowrap {
white-space: nowrap;
}
.left {
float: left;
}
.right {
float: right;
}
.clear {
background-color: transparent;
border: 0;
clear: both;
display: block;
font-size: 0;
height: 0;
line-height: 0;
overflow: hidden;
}
.none {
display: none;
}
.pointer {
cursor: pointer;
}
.no-underline {
text-decoration: none !important;
}
.red {
color: red;
}
.contentBody {
margin-bottom: 12px;
padding: 3px 12px;
}
/* start form */
.form th {
text-align: right;
white-space: nowrap;
}
.form input[type='text'], .form input[type='password'], .form textarea {
border-color: #C0C0C0 #D9D9D9 #D9D9D9;
border-right: 1px solid #D9D9D9;
border-style: solid;
border-width: 1px;
font-family: Helvetica,Arial,sans-serif;
font-size: 12px;
outline: medium none;
width: 99%;
padding: 0 3px;
}
.form input {
height: 24px;
}
.form input[type='checkbox'] {
border: 0px;
vertical-align: middle;
}
.form input.normalInput {
width: auto;
}
.form input[type='checkbox']:focus {
border: 0px;
}
.form input:focus, .form textarea:focus {
box-shadow: 0 1px 2px rgba(0, 0, 0, 0.3) inset;
}
.form textarea {
padding: 3px;
overflow: auto;
resize: vertical;
}
/* end form */
.logo {
padding: 0 5px;
text-decoration: none;
text-shadow: 0 0 1px #EEEEEE;
}
/* start icon */
.putTopIcon,.notPutTopIcon,.deleteIcon,.updateIcon,.commentIcon,
.homeIcon,.adminIcon,.loginIcon,.logoutIcon,.calendarIcon,.browserIcon,
.postIcon,.articlesIcon,.draftsIcon,.usersIcon,.linkIcon,
.preferenceIcon, .pageIcon, .trueIcon,.falseIcon,
.fileIcon, .othersIcon, .goTopIcon, .goBottomIcon, .cacheIcon, .aboutIcon {
background-image: url("../images/icon.png");
cursor: pointer;
height: 16px;
width: 16px;
}
.adminIcon,.loginIcon,.logoutIcon,.homeIcon {
margin-top: 3px;
}
.pageIcon {
background-position: -144px 0px;
}
.postIcon {
background-position: -16px 0;
}
.linkIcon {
background-position: -32px 0;
}
.preferenceIcon {
background-position: -48px 0;
}
.articlesIcon {
background-position: -64px 0;
}
.trueIcon {
background-position: -80px 0;
cursor: auto;
}
.falseIcon {
background-position: -96px 0;
cursor: auto;
}
.fileIcon {
background-position: -112px 0;
}
.deleteIcon {
background-position: 0 -16px;
}
.updateIcon {
background-position: -16px -16px;
}
.commentIcon {
background-position: -32px -16px;
}
.homeIcon {
background-position: -64px -16px;
}
.adminIcon {
background-position: -80px -16px;
}
.logoutIcon {
background-position: -96px -16px;
}
.loginIcon {
background-position: -112px -16px;
}
.browserIcon {
background-position: -128px -16px;
}
.calendarIcon {
background-position: -144px -16px;
}
.putTopIcon {
background-position: -16px -32px;
float: left;
}
.notPutTopIcon {
background-position: -32px -32px;
float: left;
}
.othersIcon {
background-position: -48px -32px;
}
.cacheIcon {
background-position: -96px -32px;
}
.draftsIcon {
background-position: -96px -32px;
}
.usersIcon {
background-position: -112px -32px;
}
.goTopIcon {
background-position: -64px -32px;
position: fixed;
right: 20px;
top: 45%;
}
.goBottomIcon {
background-position: -80px -32px;
bottom: 40%;
position: fixed;
right: 20px;
}
.article-body {
overflow: hidden;
line-height: 145%;
word-wrap: break-word;
}
.article-body blockquote {
border: 1px dotted #98A47F;
font-style: italic;
margin: 12px;
padding: 12px;
}
.article-body h1 {
font-size: 2em;
margin: .67em 0;
}
.article-body h2 {
font-size: 1.5em;
margin: .75em 0;
}
.article-body h3 {
font-size: 1.17em;
margin: .83em 0;
}
.article-body h4, .article-body p, .article-body blockquote,
.article-body ul, .article-body fieldset, .article-body form, .article-body ol,
.article-body dl, .article-body dir, .article-body menu {
margin: 1.12em 0;
}
.article-body h5 {
font-size: .83em;
margin: 1.5em 0;
}
.article-body h6 {
font-size: .75em;
margin: 1.67em 0;
}
.article-body blockquote {
margin-left: 40px;
margin-right: 40px;
}
.article-body ol, .article-body ul, .article-body dir,
.article-body menu, .article-body dd {
margin-left: 40px;
}
/* start icon */
/* start emotions */
.em00, .em01, .em02, .em03, .em04, .em05, .em06, .em07, .em08, .em09,
.em10, .em11, .em12, .em13, .em14 {
background-image: url("../images/emotions/classic/emotions-classic.png");
float: left;
height: 24px;
margin-right: 5px;
width: 24px;
}
#emotions span {
cursor: pointer;
}
.em01 {
background-position: -24px 0;
}
.em02 {
background-position: -48px 0;
}
.em03 {
background-position: -72px 0;
}
.em04 {
background-position: -96px 0;
}
.em05 {
background-position: 0px -24px;
}
.em06 {
background-position: -24px -24px;
}
.em07 {
background-position: -48px -24px;
}
.em08 {
background-position: -72px -24px;
}
.em09 {
background-position: -96px -24px;
}
.em10 {
background-position: 0 -48px;
}
.em11 {
background-position: -24px -48px ;
}
.em12 {
background-position: -48px -48px;
}
.em13 {
background-position: -72px -48px;
}
.em14 {
background-position: -96px -48px;
}
/* end emotions */
/* start tags */
#tags {
list-style: none;
}
#tags li {
float: left;
list-style: none;
height: 38px;
}
#tags a:hover {
text-shadow: 0 0 2px #555555;
}
#tags a {
border-radius: 3px 3px 3px 3px;
box-shadow: 1px 1px 3px #555555;
float: left;
margin: 3px 6px;
padding: 3px 12px;
text-decoration: none;
}
#tags .tags1 {
font-size: 12px;
font-weight: normal;
}
#tags .tags2 {
font-size: 14px;
font-weight: normal;
}
#tags .tags3 {
font-size: 16px;
font-weight: normal;
}
#tags .tags4 {
font-size: 18px;
font-weight: bold;
}
#tags .tags5 {
font-size: 20px;
font-weight: bold;
}
/* end tags */
/* start comment */
#captcha, #captchaReply {
cursor: pointer;
}
>>>>>>> origin/0.4.6
/* end comment */ /* end comment */
\ No newline at end of file
<<<<<<< HEAD
/** /**
* 403, 500, article-pwd, init, login and kill-browser page style. * 403, 500, article-pwd, init, login and kill-browser page style.
* *
...@@ -224,4 +225,256 @@ input:focus { ...@@ -224,4 +225,256 @@ input:focus {
font-weight: bold; font-weight: bold;
margin-top: 18px; margin-top: 18px;
} }
=======
/*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* 403, 404, 500, article-pwd, init, login and kill-browser page style.
*
* @author <a href="mailto:LLY219@gmail.com">Liyuan Li</a>
* @version 1.0.1.1, Jun 13, 2012
*/
html {
height: 100%;
overflow: hidden;
}
*,html,body {
margin: 0;
padding: 0;
}
body {
background-color: #F3F1E5;
color: #4D505D;
font-family: \5fae\8f6f\96c5\9ed1;
font-size: small;
height: 100%;
}
button {
background: url(../images/icon.png) repeat center bottom;
border: 1px solid;
border-color: #CCC #BBBBBB #A0A0A0;
border-radius: 4px;
height: 28px;
margin: 0;
padding: 0 6px;
vertical-align: top;
float: right;
margin: 12px 0 0 24px;
outline: none;
}
input {
background: none repeat scroll 0 0 #FBFBFB;
border: 1px solid #E5E5E5;
box-shadow: 1px 1px 2px rgba(200, 200, 200, 0.2) inset;
color: #4D505D;
font-family: Helvetica,Arial,sans-serif,\5fae\8f6f\96c5\9ed1;
font-size: 20px;
font-weight: 200;
height: 28px;
margin-top: 10px;
outline: medium none;
padding: 3px;
width: 280px;
}
input:focus {
box-shadow: 0px 0px 5px rgba(200, 200, 200, 0.9);
}
.clear {
background-color: transparent;
border: 0px;
clear: both;
display: block;
font-size: 0px;
height: 0px;
line-height: 0px;
overflow: hidden;
}
.none {
display: none;
}
.icon {
position: absolute;
right: 0px;
top: 0px;
width:16px;
height:16px;
}
.solo {
color: orangered;
font-weight: bold;
}
.logo {
float: left;
padding: 162px 12px 0;
width: 153px;
}
.wrapper {
height: auto;
min-height: 100%;
position: relative;
}
.wrap {
border-top: 5px solid #E6E5D9;
min-height: 400px;
}
.content {
background: url("../images/zz.jpg") repeat-x scroll center bottom white;
border-color: #E6E5D9;
border-style: solid solid none;
border-width: 1px;
margin: 0 auto;
position: relative;
width: 700px;
top: 60px;
}
.main {
border-left: 1px solid #E6E5D9;
float: right;
font-size: 15px;
margin: 24px 0;
padding: 12px 24px;
width: 470px;
height: 338px;
}
.main a {
text-decoration: none;
}
.main ul {
margin-bottom: 73px;
}
.main li {
margin: 6px 0 6px 16px;
}
.main p {
margin: 12px 0;
}
.mian tr {
height: 54px;
}
.footerWrapper {
background-color: #FFFFFF;
border-top: 1px solid #E6E5D9;
bottom: 0;
padding: 12px 0;
position: absolute;
text-align: center;
width: 100%;
}
.footerWrapper a {
text-decoration: none;
}
/* start article-pwd */
.article-pwd > div {
margin-bottom: 10px;
max-height: 264px;
overflow: auto;
word-wrap: break-word;
}
.article-pwd #confirm {
margin-top: 6px;
}
/* end article-pwd */
/* start 403/404/500 */
.img-404, .img-403, .img-500 {
box-shadow: 0 0 5px #E6E5D9;
margin: 20px 0 0 45px;
padding: 5px;
}
.a-404, .a-403, .a-500 {
margin: 20px 50px 0 0 ;
text-align: right;
}
.img-403 {
margin: 20px 0 0 60px;
}
.a-403 {
margin: 20px 75px 0 0 ;
}
.img-500 {
margin: 25px 0 0 25px;
}
.a-500 {
margin: 25px 35px 0 0 ;
}
/* end 403/404/500 */
/* start login */
.login table {
margin: 66px auto;
}
/* end login */
/* start kill */
.kill {
position: absolute;
right: 40px;
top: 230px;
}
/* end kill */
/* start init and login */
#init {
position: absolute;
top: 102px;
width: 470px;
}
#sys p {
height: 166px;
}
#initButton {
margin-right: 10px;
}
#tip {
color: #21759B;
float: right;
font-weight: bold;
margin-top: 18px;
}
>>>>>>> origin/0.4.6
/* end init and login */ /* end init and login */
\ No newline at end of file
...@@ -2,14 +2,8 @@ ...@@ -2,14 +2,8 @@
<html> <html>
<head> <head>
<meta charset="utf-8" /> <meta charset="utf-8" />
<meta name="robots" content="none" />
<title>${blogTitle} - 403 Forbidden!</title> <title>${blogTitle} - 403 Forbidden!</title>
<meta name="keywords" content="GAE 博客,GAE blog,b3log,init" />
<meta name="description" content="An open source blog with Java. Java 开源博客" />
<meta name="author" content="B3log Team" />
<meta name="generator" content="B3log" />
<meta name="copyright" content="B3log" />
<meta name="revised" content="B3log, ${year}" />
<meta http-equiv="Window-target" content="_top" />
<link type="text/css" rel="stylesheet" href="${staticServePath}/css/default-init${miniPostfix}.css?${staticResourceVersion}" charset="utf-8" /> <link type="text/css" rel="stylesheet" href="${staticServePath}/css/default-init${miniPostfix}.css?${staticResourceVersion}" charset="utf-8" />
<link rel="icon" type="image/png" href="${staticServePath}/favicon.png" /> <link rel="icon" type="image/png" href="${staticServePath}/favicon.png" />
</head> </head>
...@@ -24,6 +18,11 @@ ...@@ -24,6 +18,11 @@
</div> </div>
<div class="main"> <div class="main">
<h2>403 Forbidden!</h2> <h2>403 Forbidden!</h2>
<img class="img-403" src="${staticServePath}/images/403.png" alt="403: forbidden" title="403: forbidden" />
<div class="a-403">
<a href="${servePath}">Index</a> |
<a href="${loginURL}">Login</a>
</div>
<a href="http://b3log.org" target="_blank"> <a href="http://b3log.org" target="_blank">
<img border="0" class="icon" alt="B3log" title="B3log" src="${staticServePath}/favicon.png"/> <img border="0" class="icon" alt="B3log" title="B3log" src="${staticServePath}/favicon.png"/>
</a> </a>
...@@ -34,7 +33,7 @@ ...@@ -34,7 +33,7 @@
</div> </div>
<div class="footerWrapper"> <div class="footerWrapper">
<div class="footer"> <div class="footer">
&copy; 2012 &copy; ${year}
Powered by Powered by
<a href="http://b3log.org" target="_blank"> <a href="http://b3log.org" target="_blank">
<span style="color: orange;">B</span><span style="color: blue;"><sup>3</sup></span><span style="color: green;">L</span><span style="color: red;">O</span><span style="color: blue;">G</span> <span style="color: orange;">B</span><span style="color: blue;"><sup>3</sup></span><span style="color: green;">L</span><span style="color: red;">O</span><span style="color: blue;">G</span>
......
...@@ -2,14 +2,8 @@ ...@@ -2,14 +2,8 @@
<html> <html>
<head> <head>
<meta charset="utf-8" /> <meta charset="utf-8" />
<meta name="robots" content="none" />
<title>${blogTitle} - 404 Not Found!</title> <title>${blogTitle} - 404 Not Found!</title>
<meta name="keywords" content="GAE 博客,GAE blog,b3log,init" />
<meta name="description" content="An open source blog with Java. Java 开源博客" />
<meta name="author" content="B3log Team" />
<meta name="generator" content="B3log" />
<meta name="copyright" content="B3log" />
<meta name="revised" content="B3log, ${year}" />
<meta http-equiv="Window-target" content="_top" />
<link type="text/css" rel="stylesheet" href="${staticServePath}/css/default-init${miniPostfix}.css?${staticResourceVersion}" charset="utf-8" /> <link type="text/css" rel="stylesheet" href="${staticServePath}/css/default-init${miniPostfix}.css?${staticResourceVersion}" charset="utf-8" />
<link rel="icon" type="image/png" href="${staticServePath}/favicon.png" /> <link rel="icon" type="image/png" href="${staticServePath}/favicon.png" />
</head> </head>
...@@ -24,6 +18,8 @@ ...@@ -24,6 +18,8 @@
</div> </div>
<div class="main"> <div class="main">
<h2>404 Not Found!</h2> <h2>404 Not Found!</h2>
<img class="img-404" alt="404: not found" title="404: not found" src="${staticServePath}/images/404.png" />
<div class="a-404"><a href="${servePath}">Index</a></div>
<a href="http://b3log.org" target="_blank"> <a href="http://b3log.org" target="_blank">
<img border="0" class="icon" alt="B3log" title="B3log" src="${staticServePath}/favicon.png"/> <img border="0" class="icon" alt="B3log" title="B3log" src="${staticServePath}/favicon.png"/>
</a> </a>
...@@ -34,7 +30,7 @@ ...@@ -34,7 +30,7 @@
</div> </div>
<div class="footerWrapper"> <div class="footerWrapper">
<div class="footer"> <div class="footer">
&copy; 2012 &copy; ${year}
Powered by Powered by
<a href="http://b3log.org" target="_blank"> <a href="http://b3log.org" target="_blank">
<span style="color: orange;">B</span><span style="color: blue;"><sup>3</sup></span><span style="color: green;">L</span><span style="color: red;">O</span><span style="color: blue;">G</span> <span style="color: orange;">B</span><span style="color: blue;"><sup>3</sup></span><span style="color: green;">L</span><span style="color: red;">O</span><span style="color: blue;">G</span>
......
...@@ -3,13 +3,6 @@ ...@@ -3,13 +3,6 @@
<head> <head>
<meta charset="utf-8" /> <meta charset="utf-8" />
<title>${blogTitle} - 500 Internal Server Error!</title> <title>${blogTitle} - 500 Internal Server Error!</title>
<meta name="keywords" content="GAE 博客,GAE blog,b3log,init" />
<meta name="description" content="An open source blog with Java. Java 开源博客" />
<meta name="author" content="B3log Team" />
<meta name="generator" content="B3log" />
<meta name="copyright" content="B3log" />
<meta name="revised" content="B3log, ${year}" />
<meta http-equiv="Window-target" content="_top" />
<link type="text/css" rel="stylesheet" href="${staticServePath}/css/default-init${miniPostfix}.css?${staticResourceVersion}" charset="utf-8" /> <link type="text/css" rel="stylesheet" href="${staticServePath}/css/default-init${miniPostfix}.css?${staticResourceVersion}" charset="utf-8" />
<link rel="icon" type="image/png" href="${staticServePath}/favicon.png" /> <link rel="icon" type="image/png" href="${staticServePath}/favicon.png" />
</head> </head>
...@@ -24,10 +17,12 @@ ...@@ -24,10 +17,12 @@
</div> </div>
<div class="main"> <div class="main">
<h2>500 Internal Server Error!</h2> <h2>500 Internal Server Error!</h2>
<p> <img class="img-500" src="${staticServePath}/images/500.png" title="500: internal error" alt="500: internal error" />
Maybe it is a bug, please <div class="a-500">
<a href="https://github.com/b3log/b3log-solo/issues/new">report<a> it to help us. Please
</p> <a href="https://github.com/b3log/b3log-solo/issues/new">report</a> it to help us.
Return to <a href="${servePath}">Index</a>.
</div>
<a href="http://b3log.org" target="_blank"> <a href="http://b3log.org" target="_blank">
<img border="0" class="icon" alt="B3log" title="B3log" src="${staticServePath}/favicon.png"/> <img border="0" class="icon" alt="B3log" title="B3log" src="${staticServePath}/favicon.png"/>
</a> </a>
...@@ -38,7 +33,7 @@ ...@@ -38,7 +33,7 @@
</div> </div>
<div class="footerWrapper"> <div class="footerWrapper">
<div class="footer"> <div class="footer">
&copy; 2012 &copy; ${year}
Powered by Powered by
<a href="http://b3log.org" target="_blank"> <a href="http://b3log.org" target="_blank">
<span style="color: orange;">B</span><span style="color: blue;"><sup>3</sup></span><span style="color: green;">L</span><span style="color: red;">O</span><span style="color: blue;">G</span> <span style="color: orange;">B</span><span style="color: blue;"><sup>3</sup></span><span style="color: green;">L</span><span style="color: red;">O</span><span style="color: blue;">G</span>
...@@ -47,4 +42,4 @@ ...@@ -47,4 +42,4 @@
</div> </div>
</div> </div>
</body> </body>
</html> </html>
<<<<<<< HEAD
/* /*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team * Copyright (c) 2009, 2010, 2011, 2012, B3log Team
* *
...@@ -252,4 +253,260 @@ $.extend(Admin.prototype, { ...@@ -252,4 +253,260 @@ $.extend(Admin.prototype, {
this.setCurByHash(); this.setCurByHash();
} }
}); });
=======
/*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* index for admin
*
* @author <a href="mailto:LLY219@gmail.com">Liyuan Li</a>
* @version 1.0.1.9, Jun 19, 2012
*/
var Admin = function () {
this.register = {};
// 工具栏下的工具
this.tools = ['#page-list', '#file-list', '#link-list', '#preference',
'#user-list', '#plugin-list', '#others'];
// 多用户时,一般用户不能使用的功能
this.adTools = ['link-list', 'preference', 'file-list', 'page-list',
'user-list', 'plugin-list'];
};
$.extend(Admin.prototype, {
/*
* 登出
*/
logout: function () {
window.location.href = latkeConfig.servePath + "/logout?goto=" + latkeConfig.servePath;
},
/*
* 根据当前页数设置 hash
* @currentPage {string} 当前页
*/
setHashByPage: function (currentPage) {
var hash = window.location.hash,
hashList = hash.split("/");
if (/^\d*$/.test(hashList[hashList.length - 1])) {
hashList[hashList.length - 1] = currentPage;
} else {
hashList.push(currentPage);
}
window.location.hash = hashList.join("/");
},
/*
* 设置某个 tab 被选择
* @id tab id
*/
selectTab: function (id) {
window.location.hash = "#" + id;
},
/*
* 根据当前 hash 解析出当前页数及 hash 数组。
*/
analyseHash: function () {
var hash = window.location.hash;
var tag = hash.substr(1, hash.length - 1);
var tagList = tag.split("/");
var tags = {};
tags.page = 1,
tags.hashList = [];
for (var i = 0; i < tagList.length; i++) {
if (i === tagList.length - 1 && (/^\d+$/.test(tagList[i]))) {
tags.page = tagList[i];
} else {
tags.hashList.push(tagList[i]);
}
}
return tags;
},
/*
* 根据当前 hash 设置当前 tab
*/
setCurByHash: function () {
var tags = admin.analyseHash();
var tab = tags.hashList[1],
subTab = tags.hashList[2];
if (tags.hashList.length === 1) {
tab = tags.hashList[0];
}
if (tab === "") {
return;
}
// 离开编辑器时进行提示
try {
// 除更新、发布、取消发布文章,编辑器中无内容外,离开编辑器需进行提示。
if (tab !== "article" && admin.article.isConfirm &&
admin.editorArticle.getContent().replace(/\s/g, '') !== "") {
if (!confirm(Label.editorLeaveLabel)) {
window.location.hash = "#article/article";
return;
}
}
// 不离开编辑器,hash 需变为 "#article/article",此时不需要做任何处理。
if (tab === "article" && admin.article.isConfirm &&
admin.editorArticle.getContent().replace(/\s/g, '') !== "") {
return;
}
} catch (e) {
var $articleContent = $('#articleContent');
if ($articleContent.length > 0) {
if (tab !== "article" && admin.article.isConfirm &&
$articleContent.val().replace(/\s/g, '') !== "") {
if (!confirm(Label.editorLeaveLabel)) {
window.location.hash = "#article/article";
return;
}
}
// 不离开编辑器,hash 需变为 "#article/article",此时不需要做任何处理。
if (tab === "article" && admin.article.isConfirm &&
$articleContent.val().replace(/\s/g, '') !== "") {
return;
}
}
}
// clear article
if (tab !== "article" && admin.editorArticle.setContent) {
admin.article.clear();
}
admin.article.isConfirm = true;
$("#tabs").tabs("setCurrent", tab);
$("#loadMsg").text(Label.loadingLabel);
if ($("#tabsPanel_" + tab).length === 1) {
if ($("#tabsPanel_" + tab).html().replace(/\s/g, "") === "") {
// 还未加载 HTML
$("#tabsPanel_" + tab).load("admin-" + tab + ".do", function () {
// 页面加载完后,回调初始函数
if (tab === "article" && admin.article.status.id) {
// 当文章页面编辑器未初始化时,调用更新文章需先初始化编辑器
admin.register[tab].init.call(admin.register[tab].obj, admin.article.getAndSet);
} else {
admin.register[tab].init.call(admin.register[tab].obj, tags.page);
}
// 页面包含子 tab,需根据 hash 定位到相应的 tab
if (subTab) {
$("#tab" + tab.substring(0, 1).toUpperCase() + tab.substring(1)).
tabs("setCurrent", subTab);
}
// 根据 hash 调用现有的插件函数
admin.plugin.setCurByHash(tags);
});
} else {
if (tab === "article" && admin.article.status.id) {
admin.article.getAndSet();
}
// 已加载过 HTML,只需调用刷新函数
if (admin.register[tab] && admin.register[tab].refresh) {
admin.register[tab].refresh.call(admin.register[tab].obj, tags.page);
}
// 页面包含子 tab,需根据 hash 定位到相应的 tab
if (subTab) {
$("#tab" + tab.substring(0, 1).toUpperCase() + tab.substring(1)).
tabs("setCurrent", subTab);
}
// 根据 hash 调用现有的插件函数
admin.plugin.setCurByHash(tags);
}
} else {
$("#tipMsg").text("Error: No tab! " + Label.reportIssueLabel);
$("#loadMsg").text("");
}
},
/*
* 初始化整个后台
*/
init: function () {
//window.onerror = Util.error;
Util.killIE();
$("#loadMsg").text(Label.loadingLabel);
// 构建 tabs
$("#tabs").tabs();
// tipMsg
setInterval(function () {
if($("#tipMsg").text() !== "") {
setTimeout(function () {
$("#tipMsg").text("");
}, 7000);
}
}, 6000);
$("#loadMsg").text("");
},
/*
* @description tools and article collapse
* @param {bom} it 触发事件对象
*/
collapseNav: function (it) {
var subNav = $(it).next();
subNav.slideToggle("normal", function () {
if (this.style.display !== "none") {
$(it).find(".ico-arrow-down")[0].className = "ico-arrow-up";
} else {
$(it).find(".ico-arrow-up")[0].className = "ico-arrow-down";
}
});
/*if (subNav.className === "none") {
$(it).find(".ico-arrow-down")[0].className = "ico-arrow-up";
subNav.className = "collapsed";
} else {
$(it).find(".ico-arrow-up")[0].className = "ico-arrow-down";
subNav.className = "none";
}*/
},
/*
* 后台及当前页面所需插件初始化完后,对权限进行控制及当前页面属于 tools 时,tools 选项需展开。
*/
inited: function () {
// Removes functions with the current user role
if (Label.userRole !== "adminRole") {
for (var i = 0; i < this.adTools.length; i++) {
$("#tabs").tabs("remove", this.adTools[i]);
}
$("#tabs>ul>li").last().remove();
} else {
// 当前 tab 属于 Tools 时,设其展开
for (var j = 0; j < this.tools.length; j++) {
if ("#" + window.location.hash.split("/")[1] === this.tools[j]) {
$("#tabToolsTitle").click();
break;
}
}
}
this.setCurByHash();
}
});
>>>>>>> origin/0.4.6
var admin = new Admin(); var admin = new Admin();
\ No newline at end of file
<<<<<<< HEAD
/* /*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team * Copyright (c) 2009, 2010, 2011, 2012, B3log Team
* *
...@@ -94,4 +95,104 @@ admin.editors.KindEditor = { ...@@ -94,4 +95,104 @@ admin.editors.KindEditor = {
$("#" + id).val(content); $("#" + id).val(content);
} }
} }
=======
/*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* @fileoverview KindEditor
*
* @author <a href="mailto:LLY219@gmail.com">Liyuan Li</a>
* @version 1.0.0.2, Jun 19, 2012
*/
admin.editors.KindEditor = {
/*
* @description 初始化编辑器
* @param conf 编辑器初始化参数
* @param conf.kind 编辑器类型
* @param conf.id 编辑器渲染元素 id
* @param conf.fun 编辑器首次加载完成后回调函数
*/
init: function (conf) {
var language = "zh_CN";
if ("en_US" === Label.localeString) {
language = "en"
}
if (conf.kind && conf.kind === "simple") {
try {
this[conf.id] = KindEditor.create('#' + conf.id, {
langType : language,
resizeType: 0,
items: ["bold", "italic", "underline", "strikethrough", "|", "undo", "redo", "|",
"insertunorderedlist", "insertorderedlist",
]
});
} catch (e) {
$("#tipMsg").text("KindEditor load fail");
}
} else {
try {
this[conf.id] = KindEditor.create('#' + conf.id, {
langType : language,
items: ["formatblock", "fontname", "fontsize", "|", "bold", "italic", "underline", "strikethrough", "forecolor", "|",
"link", "unlink", "image", "media", "|", "pagebreak", "emoticons", "code", "/",
"undo", "redo", "|", "insertunorderedlist", "insertorderedlist", "indent", "outdent", "|",
"justifyleft", "justifycenter", "justifyright", "justifyfull", "|", "plainpaste", "wordpaste", "|",
"clearhtml", "source", "preview"
],
afterCreate: function () {
// TODO: chrome bug
window.onhashchange = admin.setCurByHash;
if (typeof(conf.fun) === "function") {
conf.fun();
}
}
});
} catch (e) {
$("#tipMsg").text("KindEditor load fail");
}
}
},
/*
* @description 获取编辑器值
* @param {string} id 编辑器id
* @returns {string} 编辑器值
*/
getContent: function (id) {
var content = "";
try {
content = this[id].html();
} catch (e) {
content = $("#" + id).val();
}
return content;
},
/*
* @description 设置编辑器值
* @param {string} id 编辑器 id
* @param {string} content 设置编辑器值
*/
setContent: function (id, content) {
try {
this[id].html(content);
} catch (e) {
$("#" + id).val(content);
}
}
>>>>>>> origin/0.4.6
}; };
\ No newline at end of file
<<<<<<< HEAD
/* /*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team * Copyright (c) 2009, 2010, 2011, 2012, B3log Team
* *
...@@ -121,4 +122,131 @@ admin.editors.tinyMCE = { ...@@ -121,4 +122,131 @@ admin.editors.tinyMCE = {
$("#" + id).val(content); $("#" + id).val(content);
} }
} }
=======
/*
* Copyright (c) 2009, 2010, 2011, 2012, B3log Team
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* @fileoverview tinyMCE editor
*
* @author <a href="mailto:LLY219@gmail.com">Liyuan Li</a>
* @version 1.0.0.5, Jun 19, 2012
*/
admin.editors.tinyMCE = {
/*
* @description 初始化编辑器
* @param conf 编辑器初始化参数
* @param conf.kind 编辑器类型
* @param conf.id 编辑器渲染元素 id
* @param conf.fun 编辑器首次加载完成后回调函数
*/
init: function (conf) {
var language = Label.localeString.substring(0, 2);
if (language === "zh") {
language = "zh-cn";
}
if (conf.kind && conf.kind === "simple") {
try {
tinyMCE.init({
// General options
language: language,
mode : "exact",
elements : conf.id,
theme : "advanced",
// Theme options
theme_advanced_buttons1 : "bold,italic,underline,strikethrough,|,undo,redo,|,bullist,numlist",
theme_advanced_buttons2 : "",
theme_advanced_buttons3 : "",
theme_advanced_toolbar_location : "top",
theme_advanced_toolbar_align : "left",
valid_children : "+body[style]"
});
} catch (e) {
$("#tipMsg").text("TinyMCE load fail");
}
} else {
try {
tinyMCE.init({
// General options
language: language,
mode : "exact",
elements : conf.id,
theme : "advanced",
plugins : "autosave,style,advhr,advimage,advlink,preview,inlinepopups,media,paste,syntaxhl,wordcount",
// Theme options
theme_advanced_buttons1 : "formatselect,fontselect,fontsizeselect,|,bold,italic,underline,strikethrough,forecolor,|,advhr,blockquote,syntaxhl,",
theme_advanced_buttons2 : "undo,redo,|,bullist,numlist,outdent,indent,|,justifyleft,justifycenter,justifyright,justifyfull,|,pastetext,pasteword,|,link,unlink,image,iespell,media,|,cleanup,code,preview,",
theme_advanced_buttons3 : "",
theme_advanced_toolbar_location : "top",
theme_advanced_toolbar_align : "left",
theme_advanced_resizing : true,
theme_advanced_statusbar_location : "bottom",
extended_valid_elements: "link[type|rel|href|charset],pre[name|class],iframe[src|width|height|name|align],+a[*]",
valid_children : "+body[style]",
relative_urls: false,
remove_script_host: false,
oninit : function () {
// TODO: chrome bug
window.onhashchange = admin.setCurByHash;
if (typeof(conf.fun) === "function") {
conf.fun();
}
}
});
} catch (e) {
$("#tipMsg").text("TinyMCE load fail");
}
}
},
/*
* @description 获取编辑器值
* @param {string} id 编辑器id
* @returns {string} 编辑器值
*/
getContent: function (id) {
var content = "";
try {
content = tinyMCE.get(id).getContent();
} catch (e) {
content = $("#" + id).val();
}
return content;
},
/*
* @description 设置编辑器值
* @param {string} id 编辑器 id
* @param {string} content 设置编辑器值
*/
setContent: function (id, content) {
try {
if (tinyMCE.get(id)) {
tinyMCE.get(id).setContent(content);
} else {
$("#" + id).val(content);
}
} catch (e) {
$("#" + id).val(content);
}
}
>>>>>>> origin/0.4.6
}; };
\ No newline at end of file
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment