mirror of https://github.com/halo-dev/halo
feat: add static deploy handlers.
parent
0f59e2fe04
commit
83e87553b7
|
@ -1,10 +1,14 @@
|
|||
package run.halo.app.controller.admin.api;
|
||||
|
||||
import io.swagger.annotations.ApiOperation;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
import run.halo.app.model.support.StaticPageFile;
|
||||
import run.halo.app.service.StaticPageService;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author ryan0up
|
||||
* @date 2019/12/25
|
||||
|
@ -19,8 +23,21 @@ public class StaticPageController {
|
|||
this.staticPageService = staticPageService;
|
||||
}
|
||||
|
||||
@GetMapping
|
||||
@ApiOperation("List static page files.")
|
||||
public List<StaticPageFile> list() {
|
||||
return staticPageService.listFile();
|
||||
}
|
||||
|
||||
@GetMapping("generate")
|
||||
@ApiOperation("Generate static page files.")
|
||||
public void generate() {
|
||||
staticPageService.generate();
|
||||
}
|
||||
|
||||
@GetMapping("deploy")
|
||||
@ApiOperation("Deploy static page to remove platform")
|
||||
public void deploy() {
|
||||
staticPageService.deploy();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,33 @@
|
|||
package run.halo.app.handler.staticdeploy;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.stereotype.Component;
|
||||
import run.halo.app.model.enums.StaticDeployType;
|
||||
import run.halo.app.service.OptionService;
|
||||
|
||||
/**
|
||||
* Git deploy handler.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
@Slf4j
|
||||
@Component
|
||||
public class GitStaticDeployHandler implements StaticDeployHandler {
|
||||
|
||||
private final OptionService optionService;
|
||||
|
||||
public GitStaticDeployHandler(OptionService optionService) {
|
||||
this.optionService = optionService;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deploy() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean supportType(StaticDeployType type) {
|
||||
return StaticDeployType.GIT.equals(type);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,33 @@
|
|||
package run.halo.app.handler.staticdeploy;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.stereotype.Component;
|
||||
import run.halo.app.model.enums.StaticDeployType;
|
||||
import run.halo.app.service.OptionService;
|
||||
|
||||
/**
|
||||
* Netlify deploy handler.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
@Slf4j
|
||||
@Component
|
||||
public class NetlifyStaticDeployHandler implements StaticDeployHandler {
|
||||
|
||||
private final OptionService optionService;
|
||||
|
||||
public NetlifyStaticDeployHandler(OptionService optionService) {
|
||||
this.optionService = optionService;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deploy() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean supportType(StaticDeployType type) {
|
||||
return StaticDeployType.NETLIFY.equals(type);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,26 @@
|
|||
package run.halo.app.handler.staticdeploy;
|
||||
|
||||
import org.springframework.lang.Nullable;
|
||||
import run.halo.app.model.enums.StaticDeployType;
|
||||
|
||||
/**
|
||||
* Static deploy handler interface class.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
public interface StaticDeployHandler {
|
||||
|
||||
/**
|
||||
* do deploy.
|
||||
*/
|
||||
void deploy();
|
||||
|
||||
/**
|
||||
* Checks if the given type is supported.
|
||||
*
|
||||
* @param type deploy type
|
||||
* @return true if supported; false or else
|
||||
*/
|
||||
boolean supportType(@Nullable StaticDeployType type);
|
||||
}
|
|
@ -0,0 +1,64 @@
|
|||
package run.halo.app.handler.staticdeploy;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.lang.NonNull;
|
||||
import org.springframework.lang.Nullable;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.util.Assert;
|
||||
import org.springframework.util.CollectionUtils;
|
||||
import run.halo.app.exception.FileOperationException;
|
||||
import run.halo.app.model.enums.StaticDeployType;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.LinkedList;
|
||||
|
||||
/**
|
||||
* Static deploy handlers.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
@Slf4j
|
||||
@Component
|
||||
public class StaticDeployHandlers {
|
||||
|
||||
private final Collection<StaticDeployHandler> staticDeployHandlers = new LinkedList<>();
|
||||
|
||||
public StaticDeployHandlers(ApplicationContext applicationContext) {
|
||||
// Add all file handler
|
||||
addFileHandlers(applicationContext.getBeansOfType(StaticDeployHandler.class).values());
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* do deploy.
|
||||
*
|
||||
* @param staticDeployType static deploy type
|
||||
*/
|
||||
public void deploy(@NonNull StaticDeployType staticDeployType) {
|
||||
Assert.notNull(staticDeployType, "Static deploy type must not be null");
|
||||
|
||||
for (StaticDeployHandler staticDeployHandler : staticDeployHandlers) {
|
||||
if (staticDeployHandler.supportType(staticDeployType)) {
|
||||
staticDeployHandler.deploy();
|
||||
}
|
||||
}
|
||||
|
||||
throw new FileOperationException("No available static deploy handler to deploy static pages").setErrorData(staticDeployType);
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds static deploy handlers.
|
||||
*
|
||||
* @param staticDeployHandlers static deploy handler collection
|
||||
* @return current file handlers
|
||||
*/
|
||||
@NonNull
|
||||
public StaticDeployHandlers addFileHandlers(@Nullable Collection<StaticDeployHandler> staticDeployHandlers) {
|
||||
if (!CollectionUtils.isEmpty(staticDeployHandlers)) {
|
||||
this.staticDeployHandlers.addAll(staticDeployHandlers);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,36 @@
|
|||
package run.halo.app.model.enums;
|
||||
|
||||
/**
|
||||
* Static deploy type.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
public enum StaticDeployType implements ValueEnum<Integer> {
|
||||
|
||||
/**
|
||||
* Deploy static pages in remote git repository, such as github pages,gitee pages,coding pages.etc.
|
||||
*/
|
||||
GIT(1),
|
||||
|
||||
/**
|
||||
* Deploy static pages in netlify.
|
||||
*/
|
||||
NETLIFY(2);
|
||||
|
||||
private Integer value;
|
||||
|
||||
StaticDeployType(Integer value) {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get enum value.
|
||||
*
|
||||
* @return enum value
|
||||
*/
|
||||
@Override
|
||||
public Integer getValue() {
|
||||
return value;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,76 @@
|
|||
package run.halo.app.model.properties;
|
||||
|
||||
/**
|
||||
* Git static deploy properties.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
public enum GitStaticDeployProperties implements PropertyEnum {
|
||||
|
||||
/**
|
||||
* Git static deploy domain.
|
||||
*/
|
||||
GIT_DOMAIN("git_static_deploy_domain", String.class, ""),
|
||||
|
||||
/**
|
||||
* Git static deploy repository.
|
||||
*/
|
||||
GIT_REPOSITORY("git_static_deploy_repository", String.class, ""),
|
||||
|
||||
/**
|
||||
* Git static deploy branch.
|
||||
*/
|
||||
GIT_BRANCH("git_static_deploy_branch", String.class, "master"),
|
||||
|
||||
/**
|
||||
* Git static deploy username.
|
||||
*/
|
||||
GIT_USERNAME("git_static_deploy_username", String.class, ""),
|
||||
|
||||
/**
|
||||
* Git static deploy email.
|
||||
*/
|
||||
GIT_EMAIL("git_static_deploy_email", String.class, ""),
|
||||
|
||||
/**
|
||||
* Git static deploy token.
|
||||
*/
|
||||
GIT_TOKEN("git_static_deploy_token", String.class, ""),
|
||||
|
||||
/**
|
||||
* Git static deploy cname.
|
||||
*/
|
||||
GIT_CNAME("git_static_deploy_cname", String.class, "");
|
||||
|
||||
private final String value;
|
||||
|
||||
private final Class<?> type;
|
||||
|
||||
private final String defaultValue;
|
||||
|
||||
GitStaticDeployProperties(String value, Class<?> type, String defaultValue) {
|
||||
this.defaultValue = defaultValue;
|
||||
if (!PropertyEnum.isSupportedType(type)) {
|
||||
throw new IllegalArgumentException("Unsupported blog property type: " + type);
|
||||
}
|
||||
|
||||
this.value = value;
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?> getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String defaultValue() {
|
||||
return defaultValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getValue() {
|
||||
return value;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,56 @@
|
|||
package run.halo.app.model.properties;
|
||||
|
||||
/**
|
||||
* Netlify static deploy properties.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
public enum NetlifyStaticDeployProperties implements PropertyEnum {
|
||||
|
||||
/**
|
||||
* Netlify static deploy domain.
|
||||
*/
|
||||
NETLIFY_DOMAIN("netlify_static_deploy_domain", String.class, ""),
|
||||
|
||||
/**
|
||||
* Netlify static deploy site id.
|
||||
*/
|
||||
NETLIFY_SITE_ID("netlify_static_deploy_site_id", String.class, ""),
|
||||
|
||||
/**
|
||||
* Netlify static deploy token.
|
||||
*/
|
||||
NETLIFY_TOKEN("netlify_static_deploy_token", String.class, "");
|
||||
|
||||
private final String value;
|
||||
|
||||
private final Class<?> type;
|
||||
|
||||
private final String defaultValue;
|
||||
|
||||
NetlifyStaticDeployProperties(String value, Class<?> type, String defaultValue) {
|
||||
this.defaultValue = defaultValue;
|
||||
if (!PropertyEnum.isSupportedType(type)) {
|
||||
throw new IllegalArgumentException("Unsupported blog property type: " + type);
|
||||
}
|
||||
|
||||
this.value = value;
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?> getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String defaultValue() {
|
||||
return defaultValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getValue() {
|
||||
return value;
|
||||
}
|
||||
}
|
|
@ -155,6 +155,9 @@ public interface PropertyEnum extends ValueEnum<String> {
|
|||
propertyEnumClasses.add(SeoProperties.class);
|
||||
propertyEnumClasses.add(UpOssProperties.class);
|
||||
propertyEnumClasses.add(ApiProperties.class);
|
||||
propertyEnumClasses.add(StaticDeployProperties.class);
|
||||
propertyEnumClasses.add(GitStaticDeployProperties.class);
|
||||
propertyEnumClasses.add(NetlifyStaticDeployProperties.class);
|
||||
|
||||
Map<String, PropertyEnum> result = new HashMap<>();
|
||||
|
||||
|
|
|
@ -0,0 +1,45 @@
|
|||
package run.halo.app.model.properties;
|
||||
|
||||
import run.halo.app.model.enums.StaticDeployType;
|
||||
|
||||
/**
|
||||
* Static deploy properties.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
public enum StaticDeployProperties implements PropertyEnum {
|
||||
|
||||
/**
|
||||
* static deploy type
|
||||
*/
|
||||
DEPLOY_TYPE("static_deploy_type", StaticDeployType.class, StaticDeployType.GIT.name());
|
||||
|
||||
private final String value;
|
||||
|
||||
private final Class<?> type;
|
||||
|
||||
private final String defaultValue;
|
||||
|
||||
|
||||
StaticDeployProperties(String value, Class<?> type, String defaultValue) {
|
||||
this.value = value;
|
||||
this.type = type;
|
||||
this.defaultValue = defaultValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?> getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String defaultValue() {
|
||||
return defaultValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getValue() {
|
||||
return value;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,35 @@
|
|||
package run.halo.app.model.support;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Static page dto.
|
||||
*
|
||||
* @author ryanwang
|
||||
* @date 2019-12-26
|
||||
*/
|
||||
@Data
|
||||
public class StaticPageFile implements Comparator<StaticPageFile> {
|
||||
|
||||
private String name;
|
||||
|
||||
private Boolean isFile;
|
||||
|
||||
private List<StaticPageFile> children;
|
||||
|
||||
@Override
|
||||
public int compare(StaticPageFile leftFile, StaticPageFile rightFile) {
|
||||
if (leftFile.isFile && !rightFile.isFile) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!leftFile.isFile && rightFile.isFile) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
return leftFile.getName().compareTo(rightFile.getName());
|
||||
}
|
||||
}
|
|
@ -1,5 +1,9 @@
|
|||
package run.halo.app.service;
|
||||
|
||||
import run.halo.app.model.support.StaticPageFile;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Static Page service interface.
|
||||
*
|
||||
|
@ -17,4 +21,16 @@ public interface StaticPageService {
|
|||
* Generate pages.
|
||||
*/
|
||||
void generate();
|
||||
|
||||
/**
|
||||
* Deploy static pages.
|
||||
*/
|
||||
void deploy();
|
||||
|
||||
/**
|
||||
* List file of generated static page.
|
||||
*
|
||||
* @return a list of generated static page.
|
||||
*/
|
||||
List<StaticPageFile> listFile();
|
||||
}
|
||||
|
|
|
@ -10,18 +10,24 @@ import org.springframework.data.domain.PageRequest;
|
|||
import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.lang.NonNull;
|
||||
import org.springframework.lang.Nullable;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.ui.ModelMap;
|
||||
import org.springframework.ui.freemarker.FreeMarkerTemplateUtils;
|
||||
import org.springframework.util.Assert;
|
||||
import org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer;
|
||||
import run.halo.app.config.properties.HaloProperties;
|
||||
import run.halo.app.exception.ServiceException;
|
||||
import run.halo.app.handler.staticdeploy.StaticDeployHandlers;
|
||||
import run.halo.app.handler.theme.config.support.ThemeProperty;
|
||||
import run.halo.app.model.dto.PhotoDTO;
|
||||
import run.halo.app.model.entity.*;
|
||||
import run.halo.app.model.enums.PostStatus;
|
||||
import run.halo.app.model.enums.StaticDeployType;
|
||||
import run.halo.app.model.properties.PostProperties;
|
||||
import run.halo.app.model.properties.StaticDeployProperties;
|
||||
import run.halo.app.model.support.HaloConst;
|
||||
import run.halo.app.model.support.StaticPageFile;
|
||||
import run.halo.app.model.vo.PostDetailVO;
|
||||
import run.halo.app.model.vo.PostListVO;
|
||||
import run.halo.app.model.vo.SheetDetailVO;
|
||||
|
@ -33,9 +39,12 @@ import java.io.IOException;
|
|||
import java.io.UnsupportedEncodingException;
|
||||
import java.net.URLEncoder;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import static org.springframework.data.domain.Sort.Direction.DESC;
|
||||
|
||||
|
@ -79,6 +88,8 @@ public class StaticPageServiceImpl implements StaticPageService {
|
|||
|
||||
private final FreeMarkerConfigurer freeMarkerConfigurer;
|
||||
|
||||
private final StaticDeployHandlers staticDeployHandlers;
|
||||
|
||||
public StaticPageServiceImpl(PostService postService,
|
||||
PostCategoryService postCategoryService,
|
||||
PostTagService postTagService,
|
||||
|
@ -92,7 +103,8 @@ public class StaticPageServiceImpl implements StaticPageService {
|
|||
ThemeService themeService,
|
||||
HaloProperties haloProperties,
|
||||
OptionService optionService,
|
||||
FreeMarkerConfigurer freeMarkerConfigurer) throws IOException {
|
||||
FreeMarkerConfigurer freeMarkerConfigurer,
|
||||
StaticDeployHandlers staticDeployHandlers) throws IOException {
|
||||
this.postService = postService;
|
||||
this.postCategoryService = postCategoryService;
|
||||
this.postTagService = postTagService;
|
||||
|
@ -107,6 +119,7 @@ public class StaticPageServiceImpl implements StaticPageService {
|
|||
this.haloProperties = haloProperties;
|
||||
this.optionService = optionService;
|
||||
this.freeMarkerConfigurer = freeMarkerConfigurer;
|
||||
this.staticDeployHandlers = staticDeployHandlers;
|
||||
|
||||
pagesDir = Paths.get(haloProperties.getWorkDir(), PAGES_FOLDER);
|
||||
FileUtils.createIfAbsent(pagesDir);
|
||||
|
@ -138,6 +151,47 @@ public class StaticPageServiceImpl implements StaticPageService {
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deploy() {
|
||||
StaticDeployType type = getStaticDeployType();
|
||||
|
||||
staticDeployHandlers.deploy(type);
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<StaticPageFile> listFile() {
|
||||
return listStaticPageFileTree(pagesDir);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private List<StaticPageFile> listStaticPageFileTree(@NonNull Path topPath) {
|
||||
Assert.notNull(topPath, "Top path must not be null");
|
||||
|
||||
if (!Files.isDirectory(topPath)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
try (Stream<Path> pathStream = Files.list(topPath)) {
|
||||
List<StaticPageFile> staticPageFiles = new LinkedList<>();
|
||||
|
||||
pathStream.forEach(path -> {
|
||||
StaticPageFile staticPageFile = new StaticPageFile();
|
||||
staticPageFile.setName(path.getFileName().toString());
|
||||
staticPageFile.setIsFile(Files.isRegularFile(path));
|
||||
if (Files.isDirectory(path)) {
|
||||
staticPageFile.setChildren(listStaticPageFileTree(path));
|
||||
}
|
||||
|
||||
staticPageFiles.add(staticPageFile);
|
||||
});
|
||||
|
||||
staticPageFiles.sort(new StaticPageFile());
|
||||
return staticPageFiles;
|
||||
} catch (IOException e) {
|
||||
throw new ServiceException("Failed to list sub files", e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Clean static pages folder
|
||||
*/
|
||||
|
@ -714,4 +768,14 @@ public class StaticPageServiceImpl implements StaticPageService {
|
|||
Path path = Paths.get(pagesDir.toString(), subPath);
|
||||
return path.toFile();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get static deploy type from options.
|
||||
*
|
||||
* @return static deploy type
|
||||
*/
|
||||
@NonNull
|
||||
private StaticDeployType getStaticDeployType() {
|
||||
return optionService.getEnumByPropertyOrDefault(StaticDeployProperties.DEPLOY_TYPE, StaticDeployType.class, StaticDeployType.GIT);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue