[DEV] initail code with karideo origin

This commit is contained in:
Edouard DUPIN 2022-06-19 19:24:04 +02:00
parent 20be9a4f04
commit 5cb6190f8e
227 changed files with 47281 additions and 0 deletions

10
.checkstyle Normal file
View File

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="UTF-8"?>
<fileset-config file-format-version="1.2.0" simple-config="true" sync-formatter="false">
<local-check-config name="Scenarium" location="/home/heero/dev/workspace-scenarium/scenarium-core/CheckStyle.xml" type="external" description="">
<additional-data name="protect-config-file" value="false"/>
</local-check-config>
<fileset name="all" enabled="true" check-config-name="Scenarium" local="true">
<file-match-pattern match-pattern="." include-pattern="true"/>
</fileset>
</fileset-config>

64
.gitignore vendored Normal file
View File

@ -0,0 +1,64 @@
# See http://help.github.com/ignore-files/ for more about ignoring files.
out
.idea
# compiled output
/dist
/dist-server
/tmp
/out-tsc
/front/dist
config.env
*.class
dataPush
node_modules
# dependencies
applicationFront/node_modules
# IDEs and editors
/.idea
.project
.classpath
.c9/
*.launch
.settings/
*.sublime-workspace
# IDE - VSCode
.vscode/*
!.vscode/settings.json
!.vscode/tasks.json
!.vscode/launch.json
!.vscode/extensions.json
# misc
/.sass-cache
/connect.lock
/coverage
/libpeerconnection.log
npm-debug.log
yarn-error.log
testem.log
/typings
# e2e
/e2e/*.js
/e2e/*.map
# System Files
.DS_Store
Thumbs.db
backPY/env
*.pyc
__pycache__
.design/
.vscode/

79
Dockerfile Normal file
View File

@ -0,0 +1,79 @@
######################################################################################
##
## buyilding-end install applications:
##
######################################################################################
FROM archlinux:base-devel AS builder
# update system
RUN pacman -Syu --noconfirm && pacman-db-upgrade \
&& pacman -S --noconfirm jdk-openjdk maven npm \
&& pacman -Scc --noconfirm
ENV PATH /tmp/node_modules/.bin:$PATH
WORKDIR /tmp
######################################################################################
##
## Build back:
##
######################################################################################
FROM builder AS buildBack
COPY back/pom.xml /tmp
COPY back/src /tmp/src/
RUN mvn clean compile assembly:single
######################################################################################
##
## Build front:
##
######################################################################################
FROM builder AS buildFront
ADD front/package-lock.json \
front/package.json \
front/karma.conf.js \
front/protractor.conf.js \
/tmp/
# install and cache app dependencies
RUN npm install
ADD front/e2e \
front/tsconfig.json \
front/tslint.json \
front/angular.json \
/tmp/
ADD front/src /tmp/src
# generate build
RUN ng build --output-path=dist --configuration=production --base-href=/karideo/ --deploy-url=/karideo/
######################################################################################
##
## Production area:
##
######################################################################################
FROM bellsoft/liberica-openjdk-alpine:latest
# add wget to manage the health check...
RUN apk add --no-cache wget
#FROM archlinux:base
#RUN pacman -Syu --noconfirm && pacman-db-upgrade
## install package
#RUN pacman -S --noconfirm jdk-openjdk wget
## intall npm
#RUN pacman -S --noconfirm npm
## clean all the caches Need only on the release environment
#RUN pacman -Scc --noconfirm
ENV LANG=C.UTF-8
COPY --from=buildBack /tmp/out/maven/*.jar /application/application.jar
COPY --from=buildFront /tmp/dist /application/karideo/
WORKDIR /application/
EXPOSE 17080
CMD ["java", "-Xms64M", "-Xmx1G", "-cp", "/application/application.jar", "org.kar.karideo.WebLauncher"]

66
back/CheckStyle.xml Executable file
View File

@ -0,0 +1,66 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE module PUBLIC "-//Checkstyle//DTD Check Configuration 1.3//EN" "https://checkstyle.org/dtds/configuration_1_3.dtd">
<!--
This configuration file was written by the eclipse-cs plugin configuration editor
-->
<!--
Checkstyle-Configuration: Marc Checks
Description:
Checkstyle configuration that checks the sun coding conventions.
-->
<module name="Checker">
<property name="severity" value="error"/>
<property name="fileExtensions" value="java, properties, xml"/>
<module name="TreeWalker">
<module name="ConstantName"/>
<module name="LocalFinalVariableName"/>
<module name="LocalVariableName"/>
<module name="MemberName"/>
<module name="MethodName"/>
<module name="PackageName"/>
<module name="ParameterName"/>
<module name="StaticVariableName"/>
<module name="TypeName"/>
<module name="AvoidStarImport"/>
<module name="IllegalImport"/>
<module name="RedundantImport"/>
<module name="UnusedImports">
<property name="processJavadoc" value="false"/>
</module>
<module name="ModifierOrder"/>
<module name="EmptyStatement"/>
<module name="EqualsHashCode"/>
<module name="IllegalInstantiation"/>
<module name="MissingSwitchDefault"/>
<module name="SimplifyBooleanExpression"/>
<module name="SimplifyBooleanReturn"/>
<module name="HideUtilityClassConstructor"/>
<module name="InterfaceIsType"/>
<module name="ArrayTypeStyle"/>
<module name="TodoComment"/>
<module name="UpperEll"/>
<module name="AnnotationUseStyle"/>
<module name="MissingDeprecated"/>
<module name="MissingOverride"/>
<module name="PackageAnnotation"/>
<module name="SuppressWarnings"/>
<module name="AnnotationLocation"/>
<module name="ClassTypeParameterName"/>
<module name="MethodTypeParameterName"/>
<module name="InterfaceTypeParameterName"/>
<module name="CatchParameterName"/>
<module name="LambdaParameterName"/>
<module name="Regexp"/>
<module name="RegexpSinglelineJava"/>
</module>
<module name="BeforeExecutionExclusionFileFilter">
<property name="fileNamePattern" value="module\-info\.java$"/>
</module>
<module name="Translation"/>
<module name="Header"/>
<module name="RegexpHeader"/>
<module name="RegexpMultiline"/>
<module name="RegexpOnFilename"/>
<module name="RegexpSingleline"/>
</module>

66
back/CleanUp.xml Normal file
View File

@ -0,0 +1,66 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE xml>
<profiles version="2">
<profile kind="CleanUpProfile" name="Scenarium" version="2">
<setting id="cleanup.use_autoboxing" value="false"/>
<setting id="cleanup.qualify_static_method_accesses_with_declaring_class" value="false"/>
<setting id="cleanup.always_use_this_for_non_static_method_access" value="false"/>
<setting id="cleanup.organize_imports" value="true"/>
<setting id="cleanup.remove_trailing_whitespaces_ignore_empty" value="false"/>
<setting id="cleanup.format_source_code_changes_only" value="false"/>
<setting id="cleanup.qualify_static_field_accesses_with_declaring_class" value="false"/>
<setting id="cleanup.add_generated_serial_version_id" value="false"/>
<setting id="cleanup.remove_redundant_semicolons" value="false"/>
<setting id="cleanup.qualify_static_member_accesses_through_subtypes_with_declaring_class" value="true"/>
<setting id="cleanup.remove_redundant_type_arguments" value="true"/>
<setting id="cleanup.remove_unused_imports" value="true"/>
<setting id="cleanup.insert_inferred_type_arguments" value="false"/>
<setting id="cleanup.make_private_fields_final" value="true"/>
<setting id="cleanup.use_lambda" value="true"/>
<setting id="cleanup.always_use_blocks" value="false"/>
<setting id="cleanup.use_this_for_non_static_field_access_only_if_necessary" value="false"/>
<setting id="cleanup.sort_members_all" value="false"/>
<setting id="cleanup.remove_trailing_whitespaces_all" value="true"/>
<setting id="cleanup.add_missing_annotations" value="true"/>
<setting id="cleanup.always_use_this_for_non_static_field_access" value="true"/>
<setting id="cleanup.make_parameters_final" value="false"/>
<setting id="cleanup.sort_members" value="false"/>
<setting id="cleanup.remove_private_constructors" value="true"/>
<setting id="cleanup.always_use_parentheses_in_expressions" value="false"/>
<setting id="cleanup.remove_unused_local_variables" value="false"/>
<setting id="cleanup.convert_to_enhanced_for_loop" value="false"/>
<setting id="cleanup.remove_unused_private_fields" value="true"/>
<setting id="cleanup.remove_redundant_modifiers" value="false"/>
<setting id="cleanup.never_use_blocks" value="true"/>
<setting id="cleanup.add_missing_deprecated_annotations" value="true"/>
<setting id="cleanup.use_this_for_non_static_field_access" value="true"/>
<setting id="cleanup.remove_unnecessary_nls_tags" value="true"/>
<setting id="cleanup.qualify_static_member_accesses_through_instances_with_declaring_class" value="true"/>
<setting id="cleanup.add_missing_nls_tags" value="false"/>
<setting id="cleanup.remove_unnecessary_casts" value="true"/>
<setting id="cleanup.use_unboxing" value="false"/>
<setting id="cleanup.use_blocks_only_for_return_and_throw" value="false"/>
<setting id="cleanup.format_source_code" value="true"/>
<setting id="cleanup.convert_functional_interfaces" value="true"/>
<setting id="cleanup.add_default_serial_version_id" value="true"/>
<setting id="cleanup.remove_unused_private_methods" value="true"/>
<setting id="cleanup.remove_trailing_whitespaces" value="true"/>
<setting id="cleanup.make_type_abstract_if_missing_method" value="false"/>
<setting id="cleanup.add_serial_version_id" value="true"/>
<setting id="cleanup.use_this_for_non_static_method_access" value="false"/>
<setting id="cleanup.use_this_for_non_static_method_access_only_if_necessary" value="true"/>
<setting id="cleanup.use_anonymous_class_creation" value="false"/>
<setting id="cleanup.add_missing_override_annotations_interface_methods" value="true"/>
<setting id="cleanup.remove_unused_private_members" value="false"/>
<setting id="cleanup.make_local_variable_final" value="false"/>
<setting id="cleanup.add_missing_methods" value="false"/>
<setting id="cleanup.never_use_parentheses_in_expressions" value="true"/>
<setting id="cleanup.qualify_static_member_accesses_with_declaring_class" value="true"/>
<setting id="cleanup.use_parentheses_in_expressions" value="true"/>
<setting id="cleanup.add_missing_override_annotations" value="true"/>
<setting id="cleanup.use_blocks" value="true"/>
<setting id="cleanup.make_variable_declarations_final" value="true"/>
<setting id="cleanup.correct_indentation" value="true"/>
<setting id="cleanup.remove_unused_private_types" value="true"/>
</profile>
</profiles>

21
back/Dockerfile Normal file
View File

@ -0,0 +1,21 @@
FROM maven:3.6.3-openjdk-16 AS build
COPY pom.xml /tmp/
COPY src /tmp/src/
WORKDIR /tmp/
RUN mvn clean compile assembly:single
FROM bellsoft/liberica-openjdk-alpine:latest
ENV LANG=C.UTF-8
RUN mkdir /application/
COPY --from=build /tmp/out/maven/*.jar /application/application.jar
WORKDIR /application/
EXPOSE 18080
CMD ["java", "-Xms64M", "-Xmx1G", "-cp", "/application/application.jar", "org.kar.karideo.WebLauncher"]

366
back/Formatter.xml Normal file
View File

@ -0,0 +1,366 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE xml>
<profiles version="18">
<profile kind="CodeFormatterProfile" name="Scenarium" version="18">
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_ellipsis" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_for_statment" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_block_boundaries" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_logical_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_package" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_method_invocation" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_imports" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_switch_statement" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.comment.format_javadoc_comments" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.indentation.size" value="4"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_enum_constant_declaration" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_arrow_in_switch_default" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.align_with_spaces" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.disabling_tag" value="@formatter:off"/>
<setting id="org.eclipse.jdt.core.formatter.continuation_indentation" value="2"/>
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_before_code_block" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_switch_case_expressions" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_enum_constants" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_imports" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_end_of_method_body" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_package" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_if_while_statement" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.indent_root_tags" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_or_operator_multicatch" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.enabling_tag" value="@formatter:on"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.count_line_length_from_starting_position" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_arrow_in_switch_case" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_multiplicative_operator" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_field" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_method" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameterized_type_references" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_logical_operator" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_annotation_declaration_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_enum_constant" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_multiplicative_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_block" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.align_tags_descriptions_grouped" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.comment.line_length" value="200"/>
<setting id="org.eclipse.jdt.core.formatter.use_on_off_tags" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.keep_method_body_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_loop_body_block_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.preserve_white_space_between_code_and_line_comments" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_method_declaration" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_abstract_method" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.keep_enum_constant_declaration_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.align_variable_declarations_on_columns" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_union_type_in_multicatch" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_type_declaration_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_catch_clause" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_additive_operator" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_relational_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiplicative_operator" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.keep_anonymous_type_declaration_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_switch_case_expressions" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_shift_operator" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_lambda_body" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_end_of_code_block" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.compact_else_if" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_bitwise_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_type_parameters" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_loops" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_try" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_simple_for_body_on_same_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_relational_operator" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_unary_operator" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.format_line_comment_starting_on_first_column" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_annotation" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_ellipsis" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_additive_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_try_resources" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_string_concatenation" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.format_line_comments" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.text_block_indentation" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.align_type_members_on_columns" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_assignment" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_module_statements" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_after_code_block" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.comment.align_tags_names_descriptions" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.keep_if_then_body_block_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression" value="80"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.align_assignment_statements_on_columns" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_type" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block_in_case" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_arrow_in_switch_default" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_between_different_tags" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression_chain" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.comment.format_header" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_additive_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_method_declaration" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.join_wrapped_lines" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_conditional_operator" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_shift_operator" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.align_fields_grouping_blank_lines" value="2147483647"/>
<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_javadoc_boundaries" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_bitwise_operator" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_resources_in_try" value="80"/>
<setting id="org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_try_clause" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.keep_code_block_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.tabulation.size" value="4"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_bitwise_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.format_source_code" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_try" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_try_resources" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_field" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer" value="2"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_method" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_assignment_operator" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_not_operator" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_switch" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_type_annotation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.format_html" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_method_delcaration" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_if" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.keep_lambda_body_block_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.indent_empty_lines" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_type_arguments" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_unary_operator" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_annotation" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_label" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_arrow_in_switch_case" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_member_type" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_logical_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_bitwise_operator" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_relational_operator" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_try" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.format_block_comments" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_lambda_arrow" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.indent_tag_description" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_string_concatenation" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_last_class_body_declaration" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_body" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiple_fields" value="16"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_simple_while_body_on_same_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_array_initializer" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_logical_operator" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_shift_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_statement_group_in_switch" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.parentheses_positions_in_lambda_declaration" value="common_lines"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_shift_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_simple_do_while_body_on_same_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.keep_enum_declaration_on_one_line" value="one_line_if_empty"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_outer_expressions_when_nested" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_constant" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.brace_position_for_type_declaration" value="end_of_line"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_multiplicative_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_package" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_for_loop_header" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_additive_operator" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.keep_simple_getter_setter_on_one_line" value="false"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_string_concatenation" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_lambda_arrow" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.join_lines_in_comments" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.comment.indent_parameter_description" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_code_block" value="0"/>
<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.tabulation.char" value="tab"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_relational_operator" value="insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.wrap_before_string_concatenation" value="true"/>
<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_import_groups" value="1"/>
<setting id="org.eclipse.jdt.core.formatter.lineSplit" value="200"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation" value="do not insert"/>
<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch" value="insert"/>
</profile>
</profiles>

6
back/LICENSE Normal file
View File

@ -0,0 +1,6 @@
PROPIETARY licence
==================
Copyright at Edouard DUPIN
you have no right

17
back/README.md Normal file
View File

@ -0,0 +1,17 @@
Generic backend for karusic in java
===================================
mvn install
// create a single package jar
mvn clean compile assembly:single
java -cp out/maven/karusic-0.1.0-jar-with-dependencies.jar org.kar.karideo.WebLauncher

4
back/db.sql Normal file
View File

@ -0,0 +1,4 @@

View File

@ -0,0 +1,115 @@
<?xml version="1.0" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd">
<svg version="1.0" xmlns="http://www.w3.org/2000/svg"
width="1279.000000pt" height="1280.000000pt" viewBox="0 0 1279.000000 1280.000000"
preserveAspectRatio="xMidYMid meet">
<metadata>
Created by potrace 1.15, written by Peter Selinger 2001-2017
</metadata>
<g transform="translate(0.000000,1280.000000) scale(0.100000,-0.100000)"
fill="#000000" stroke="none">
<path d="M8860 12794 c-14 -2 -59 -9 -100 -15 -239 -33 -517 -147 -776 -317
-253 -167 -443 -325 -819 -682 -289 -274 -407 -378 -542 -479 -519 -386 -1257
-658 -2443 -901 l-156 -32 -89 58 c-553 357 -1131 620 -1767 804 -195 57 -477
122 -628 146 -125 19 -378 22 -470 5 -396 -73 -610 -344 -660 -836 -17 -158
-8 -489 20 -755 94 -917 291 -1732 625 -2595 130 -336 155 -428 155 -568 -1
-133 -47 -238 -167 -378 -26 -31 -117 -129 -200 -218 -84 -89 -193 -216 -242
-281 -327 -434 -515 -957 -583 -1620 -17 -164 -17 -713 0 -895 41 -446 102
-807 228 -1360 75 -325 82 -363 100 -490 18 -130 46 -197 103 -251 33 -32 139
-89 148 -80 2 1 -15 56 -37 122 -331 981 -467 2193 -345 3069 63 449 180 794
364 1066 84 125 155 206 249 283 417 340 958 352 1592 35 731 -366 1229 -927
1365 -1539 26 -118 31 -375 10 -501 -81 -484 -404 -847 -863 -971 -121 -33
-373 -37 -520 -9 -458 88 -858 409 -1068 857 -25 55 -62 131 -80 171 -64 135
-170 194 -224 125 -50 -62 -4 -272 106 -482 83 -160 174 -280 324 -431 228
-229 457 -359 755 -427 138 -32 259 -42 645 -52 374 -10 459 -19 603 -65 115
-37 218 -87 326 -159 133 -89 222 -165 476 -406 251 -238 343 -317 469 -402
118 -79 219 -129 347 -171 94 -32 188 -52 609 -132 404 -78 626 -196 775 -414
l46 -68 -25 -89 c-67 -241 -97 -383 -87 -403 12 -22 107 -61 151 -61 58 0 66
17 130 273 86 350 118 437 206 568 110 164 210 287 348 425 394 392 882 646
1363 709 611 80 1175 -201 1482 -740 132 -232 196 -482 189 -743 l-3 -132 30
-12 c96 -40 221 27 261 139 18 52 17 209 -2 318 -47 272 -223 638 -431 895
-61 75 -221 235 -320 320 l-53 45 236 415 c707 1245 769 1347 864 1433 94 85
219 109 337 65 78 -28 185 -136 231 -229 96 -197 82 -365 -63 -767 -116 -325
-141 -460 -132 -720 8 -257 61 -471 177 -711 149 -307 359 -552 628 -732 123
-83 235 -137 379 -185 180 -61 272 -48 338 45 l30 43 -2 236 c-4 659 -168
1348 -472 1977 -103 213 -190 365 -326 570 -138 207 -243 342 -456 585 -195
223 -275 333 -340 465 -66 136 -89 237 -89 395 0 160 16 253 94 563 104 407
141 633 155 939 22 501 -50 960 -239 1510 -33 97 -128 346 -211 555 -364 913
-411 1112 -454 1933 -24 472 -43 684 -76 880 -79 471 -251 842 -508 1101 -185
185 -377 292 -623 345 -70 15 -326 27 -378 18z m310 -389 c418 -154 764 -684
909 -1391 108 -528 85 -1038 -69 -1488 -33 -99 -38 -156 -15 -200 8 -15 57
-85 109 -155 564 -762 742 -1203 850 -2111 61 -511 54 -960 -25 -1530 -45
-325 -135 -704 -195 -821 -7 -15 -50 -134 -95 -265 -44 -131 -103 -288 -130
-349 -194 -433 -500 -797 -942 -1118 -234 -171 -447 -291 -883 -498 -1049
-498 -1480 -649 -1998 -700 -175 -17 -564 -6 -736 20 -370 58 -792 181 -1245
363 -458 184 -929 419 -971 483 -24 37 -11 67 55 124 33 29 83 84 112 124 29
40 73 99 97 132 54 72 105 178 127 260 23 84 30 291 16 411 -18 141 -54 305
-116 526 -122 439 -218 648 -386 848 -30 36 -77 94 -104 130 -28 36 -78 96
-112 133 -96 105 -96 126 1 238 35 41 100 116 145 168 219 254 389 514 675
1034 277 502 376 870 445 1652 40 444 37 631 -13 829 -44 172 -163 438 -242
542 -49 64 -64 98 -64 149 0 41 5 51 45 94 95 102 276 168 815 299 380 93 898
177 1175 191 102 5 150 12 177 25 68 33 188 172 323 374 71 106 165 237 209
290 104 125 381 407 508 520 360 316 881 621 1175 686 109 25 279 16 373 -19z
m-7618 -2080 c128 -22 260 -69 398 -142 439 -231 634 -454 690 -793 32 -188
-30 -385 -184 -590 -123 -164 -422 -426 -566 -497 -173 -85 -303 -10 -472 273
-146 245 -255 484 -322 707 -44 145 -122 492 -136 601 -29 233 80 406 280 445
72 14 220 12 312 -4z"/>
<path d="M8851 11829 c-71 -12 -216 -61 -288 -98 -259 -131 -535 -391 -766
-724 -137 -196 -187 -308 -187 -419 0 -132 69 -206 275 -293 50 -21 252 -119
449 -218 198 -98 387 -190 420 -202 177 -66 342 -72 461 -17 221 104 336 414
322 872 -6 190 -21 294 -86 585 -44 196 -55 235 -96 314 -85 168 -265 239
-504 200z m64 -342 c64 -67 101 -182 179 -547 47 -223 67 -393 69 -586 2 -146
0 -164 -17 -183 -37 -41 -114 -24 -335 70 -210 90 -382 193 -576 344 -163 127
-194 188 -142 284 37 70 256 350 350 448 138 143 260 212 376 213 51 0 57 -3
96 -43z"/>
<path d="M8896 7075 c-33 -13 -110 -58 -170 -98 -61 -41 -150 -100 -197 -131
-98 -63 -185 -152 -220 -223 -35 -72 -38 -174 -7 -232 36 -68 87 -103 153
-109 53 -4 57 -3 89 32 23 24 48 72 76 143 69 180 119 240 260 306 113 54 177
42 294 -55 32 -27 73 -56 90 -66 42 -22 141 -22 184 1 69 37 92 129 53 206
-30 58 -123 137 -215 181 -156 75 -282 90 -390 45z"/>
<path d="M10005 6115 c-133 -23 -455 -129 -567 -186 -47 -24 -78 -64 -78 -101
0 -39 32 -100 70 -132 51 -42 99 -36 233 29 98 48 126 57 222 71 86 12 126 24
184 52 85 43 92 55 95 159 1 60 -2 75 -19 91 -28 28 -60 31 -140 17z"/>
<path d="M4960 5864 c-14 -2 -52 -9 -85 -15 -143 -25 -289 -131 -389 -282
-146 -222 -157 -309 -46 -384 44 -31 106 -30 151 0 21 14 49 50 74 97 52 97
186 236 266 274 115 55 216 53 379 -9 109 -41 160 -44 221 -12 84 45 90 109
18 191 -61 70 -113 91 -289 120 -93 16 -261 27 -300 20z"/>
<path d="M10045 5513 c-332 -90 -336 -92 -371 -128 -34 -37 -49 -87 -34 -115
5 -10 24 -23 41 -29 58 -20 114 -13 226 30 99 38 117 41 223 45 146 5 244 21
263 42 40 45 32 125 -18 177 -29 31 -38 35 -81 34 -27 -1 -139 -26 -249 -56z"/>
<path d="M7263 5475 c-261 -47 -493 -195 -623 -396 -63 -98 -77 -186 -41 -264
42 -90 132 -142 318 -181 267 -56 316 -74 332 -117 19 -49 62 -389 62 -490 0
-96 -4 -117 -37 -217 -58 -176 -123 -258 -246 -315 -193 -88 -433 -28 -636
159 -51 46 -108 90 -127 96 -53 18 -98 -8 -131 -76 -23 -48 -26 -63 -22 -124
8 -113 72 -196 203 -262 158 -81 327 -113 544 -105 286 10 431 83 523 260 77
148 159 236 242 258 36 10 49 9 106 -12 59 -22 84 -24 260 -27 107 -2 253 1
324 7 156 13 204 32 295 117 35 32 107 95 159 139 127 106 138 128 164 331 12
92 17 175 13 201 -8 55 -51 106 -103 121 -53 16 -155 15 -195 -2 -62 -26 -70
-45 -78 -179 -9 -136 -37 -262 -70 -309 -30 -42 -101 -85 -184 -111 -89 -28
-266 -30 -365 -4 -151 40 -271 128 -304 222 -8 26 -20 93 -27 149 -21 189 10
317 129 534 116 209 135 255 140 341 3 71 2 79 -26 123 -58 90 -226 148 -422
147 -58 0 -137 -7 -177 -14z"/>
<path d="M9828 4739 c-44 -13 -88 -60 -88 -95 0 -40 25 -88 61 -118 32 -27 36
-28 99 -20 142 18 180 12 282 -39 102 -51 140 -57 193 -31 43 20 135 117 135
142 0 56 -99 111 -257 143 -115 23 -369 34 -425 18z"/>
<path d="M4855 4609 c-171 -59 -384 -188 -478 -289 -56 -60 -86 -123 -74 -154
11 -29 57 -39 114 -28 68 14 505 196 566 236 68 45 76 168 15 234 -27 28 -64
28 -143 1z"/>
<path d="M4830 3973 c-14 -2 -60 -15 -102 -29 -195 -64 -340 -225 -308 -343
14 -52 62 -108 101 -116 43 -10 125 33 185 96 27 28 58 56 69 62 12 6 71 11
140 12 104 0 126 4 162 23 70 37 88 93 54 167 -46 102 -162 151 -301 128z"/>
<path d="M4955 3331 c-46 -21 -106 -77 -227 -215 -117 -131 -132 -191 -66
-256 89 -89 261 -41 354 100 35 52 61 67 144 85 139 29 180 62 180 146 0 57
-18 80 -85 109 -47 20 -188 50 -234 50 -14 0 -44 -9 -66 -19z"/>
<path d="M3003 4475 c-34 -15 -37 -23 -33 -95 5 -94 71 -212 180 -320 86 -87
153 -125 201 -115 42 9 95 59 109 100 15 46 3 83 -59 177 -95 145 -182 220
-290 252 -65 19 -67 19 -108 1z"/>
<path d="M2341 4194 c-13 -9 -29 -32 -37 -50 -25 -60 -19 -78 47 -136 70 -60
99 -106 133 -205 45 -131 81 -159 188 -147 83 9 102 29 95 98 -10 94 -53 189
-118 260 -98 107 -222 196 -271 196 -8 0 -24 -7 -37 -16z"/>
<path d="M1684 3875 c-26 -40 -14 -104 34 -177 56 -87 87 -157 116 -267 14
-52 33 -102 41 -110 10 -10 33 -16 61 -16 40 0 50 5 79 36 83 91 38 290 -100
438 -108 115 -195 151 -231 96z"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 7.6 KiB

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 5.4 KiB

View File

@ -0,0 +1,77 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
version="1.1"
id="svg2"
width="225"
height="225"
viewBox="0 0 225 225"
sodipodi:docname="type_documentary.svg"
inkscape:version="0.92.4 5da689c313, 2019-01-14">
<metadata
id="metadata8">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs6" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1918"
inkscape:window-height="1038"
id="namedview4"
showgrid="false"
inkscape:zoom="2.0977778"
inkscape:cx="69.686932"
inkscape:cy="51.888857"
inkscape:window-x="0"
inkscape:window-y="20"
inkscape:window-maximized="1"
inkscape:current-layer="svg2" />
<rect
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:22.32067108;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="rect821"
width="189.09904"
height="194.34268"
x="19.142218"
y="14.375268"
ry="28.992929" />
<path
style="fill:none;stroke:#000000;stroke-width:8.39999962;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
d="m 68.167373,163.98305 19.544491,-54.34322 25.264826,30.03178 41.47246,-63.877119 33.84534,85.805089"
id="path825"
inkscape:connector-curvature="0" />
<path
style="fill:none;stroke:#000000;stroke-width:12.19999981;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
d="M 17.161017,161.59958 H 212.60593"
id="path823"
inkscape:connector-curvature="0" />
<circle
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:12.69999981;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="path827"
cx="58.633472"
cy="56.25"
r="19.544491" />
</svg>

After

Width:  |  Height:  |  Size: 2.7 KiB

View File

@ -0,0 +1,132 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Generator: Adobe Illustrator 16.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
version="1.1"
id="Capa_1"
x="0px"
y="0px"
width="100"
height="100"
viewBox="0 0 99.999999 99.999999"
xml:space="preserve"
sodipodi:docname="type_film-short.svg"
inkscape:version="0.92.4 5da689c313, 2019-01-14"><metadata
id="metadata43"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs41" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1918"
inkscape:window-height="1038"
id="namedview39"
showgrid="true"
inkscape:zoom="4.7895499"
inkscape:cx="73.393795"
inkscape:cy="42.536152"
inkscape:window-x="0"
inkscape:window-y="20"
inkscape:window-maximized="1"
inkscape:current-layer="Capa_1"><inkscape:grid
type="xygrid"
id="grid871" /></sodipodi:namedview>
<g
id="g8"
transform="translate(0,-457.47101)">
</g>
<g
id="g10"
transform="translate(0,-457.47101)">
</g>
<g
id="g12"
transform="translate(0,-457.47101)">
</g>
<g
id="g14"
transform="translate(0,-457.47101)">
</g>
<g
id="g16"
transform="translate(0,-457.47101)">
</g>
<g
id="g18"
transform="translate(0,-457.47101)">
</g>
<g
id="g20"
transform="translate(0,-457.47101)">
</g>
<g
id="g22"
transform="translate(0,-457.47101)">
</g>
<g
id="g24"
transform="translate(0,-457.47101)">
</g>
<g
id="g26"
transform="translate(0,-457.47101)">
</g>
<g
id="g28"
transform="translate(0,-457.47101)">
</g>
<g
id="g30"
transform="translate(0,-457.47101)">
</g>
<g
id="g32"
transform="translate(0,-457.47101)">
</g>
<g
id="g34"
transform="translate(0,-457.47101)">
</g>
<g
id="g36"
transform="translate(0,-457.47101)">
</g>
<path
style="fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.77471006;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
d="M 5 5 L 5 95 L 95 95 L 95 5 L 5 5 z M 40 27 L 60 27 L 60 33 L 40 33 L 40 27 z M 40 67 L 60 67 L 60 73 L 40 73 L 40 67 z "
id="rect869" /><rect
style="fill:#d5d5d5;fill-opacity:0.70980394;stroke:none;stroke-width:0.77471006;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="rect869-2"
width="70"
height="20"
x="15"
y="5"
ry="0" /><rect
style="fill:#d5d5d5;fill-opacity:0.70980394;stroke:none;stroke-width:0.94586086;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="rect869-2-3"
width="70"
height="29.81303"
x="15"
y="35"
ry="0" /><rect
style="fill:#d5d5d5;fill-opacity:0.70980394;stroke:none;stroke-width:0.77471006;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="rect869-2-7"
width="70"
height="20"
x="15"
y="75"
ry="0" /></svg>

After

Width:  |  Height:  |  Size: 3.6 KiB

View File

@ -0,0 +1,118 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Generator: Adobe Illustrator 16.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
version="1.1"
id="Capa_1"
x="0px"
y="0px"
width="100"
height="100"
viewBox="0 0 99.999999 99.999999"
xml:space="preserve"
sodipodi:docname="type_film.svg"
inkscape:version="0.92.4 5da689c313, 2019-01-14"><metadata
id="metadata43"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs41" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1918"
inkscape:window-height="1038"
id="namedview39"
showgrid="true"
inkscape:zoom="76.632798"
inkscape:cx="15.14015"
inkscape:cy="5.9693833"
inkscape:window-x="0"
inkscape:window-y="20"
inkscape:window-maximized="1"
inkscape:current-layer="Capa_1"><inkscape:grid
type="xygrid"
id="grid871" /></sodipodi:namedview>
<g
id="g8"
transform="translate(0,-457.47101)">
</g>
<g
id="g10"
transform="translate(0,-457.47101)">
</g>
<g
id="g12"
transform="translate(0,-457.47101)">
</g>
<g
id="g14"
transform="translate(0,-457.47101)">
</g>
<g
id="g16"
transform="translate(0,-457.47101)">
</g>
<g
id="g18"
transform="translate(0,-457.47101)">
</g>
<g
id="g20"
transform="translate(0,-457.47101)">
</g>
<g
id="g22"
transform="translate(0,-457.47101)">
</g>
<g
id="g24"
transform="translate(0,-457.47101)">
</g>
<g
id="g26"
transform="translate(0,-457.47101)">
</g>
<g
id="g28"
transform="translate(0,-457.47101)">
</g>
<g
id="g30"
transform="translate(0,-457.47101)">
</g>
<g
id="g32"
transform="translate(0,-457.47101)">
</g>
<g
id="g34"
transform="translate(0,-457.47101)">
</g>
<g
id="g36"
transform="translate(0,-457.47101)">
</g>
<path
style="fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.77471006;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
d="M 3,5 V 95 H 16 V 85 H 84 V 95 H 97 V 5 H 84 V 15 H 16 V 5 Z m 4,2 h 5 v 8 H 7 Z m 81,0 h 5 v 8 H 88 Z M 7,20 h 5 v 8 H 7 Z m 9,0 H 84 V 80 H 16 Z m 72,0 h 5 v 8 H 88 Z M 7,33 h 5 v 8 H 7 Z m 81,0 h 5 v 8 H 88 Z M 7,46 h 5 v 8 H 7 Z m 81,0 h 5 v 8 H 88 Z M 7,59 h 5 v 8 H 7 Z m 81,0 h 5 v 8 H 88 Z M 7,72 h 5 v 8 H 7 Z m 81,0 h 5 v 8 H 88 Z M 7,85 h 5 v 8 H 7 Z m 81,0 h 5 v 8 h -5 z"
id="rect869"
inkscape:connector-curvature="0"
sodipodi:nodetypes="cccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccc" /><path
style="fill:#dddddd;fill-opacity:0.67843137;stroke:none;stroke-width:1.34183729;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
d="M 16,5 V 15 H 84 V 5 Z m 0,15 V 80 H 84 V 20 Z m 0,65 V 95 H 84 V 85 Z"
id="rect869-2-7"
inkscape:connector-curvature="0"
sodipodi:nodetypes="ccccccccccccccc" /></svg>

After

Width:  |  Height:  |  Size: 3.6 KiB

View File

@ -0,0 +1,84 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Generator: Adobe Illustrator 17.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
version="1.1"
id="Layer_1"
x="0px"
y="0px"
width="100"
height="100"
viewBox="0 0 100 100"
enable-background="new 0 0 612 792"
xml:space="preserve"
sodipodi:docname="type_one-man-show.svg"
inkscape:version="0.92.4 5da689c313, 2019-01-14"><metadata
id="metadata15"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs13" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1918"
inkscape:window-height="1038"
id="namedview11"
showgrid="false"
inkscape:zoom="6.7425131"
inkscape:cx="53.136368"
inkscape:cy="20.736479"
inkscape:window-x="0"
inkscape:window-y="20"
inkscape:window-maximized="1"
inkscape:current-layer="Layer_1" />
<g
id="g8"
transform="matrix(0.16745942,0,0,0.17111299,-0.7543833,-17.546408)">
<path
d="m 250.576,444.206 c -6.72,-1.069 -13.312,-0.929 -19.757,1.501 C 149.234,476.476 91.05,555.361 91.05,647.579 c 0,5.51 4.468,9.978 9.978,9.978 h 411.356 c 5.51,0 9.978,-4.468 9.978,-9.978 0,-91.746 -57.589,-170.295 -138.517,-201.396 -5.753,-2.211 -11.624,-2.637 -17.6,-2.025 z"
id="path2"
inkscape:connector-curvature="0"
sodipodi:nodetypes="ccssssccc" />
<path
d="m 428.313,323.066 8.053,-21.844 -41.488,-15.296 39.978,-108.437 -114.511,-42.217 -39.978,108.437 -41.488,-15.296 -8.053,21.844 z"
id="path6"
inkscape:connector-curvature="0"
sodipodi:nodetypes="ccccccccc" />
</g>
<ellipse
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:4.5;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="path825"
cx="50.352142"
cy="44.011974"
rx="15.572829"
ry="15.276203" /><ellipse
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:4.5;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="path827"
cx="44.19717"
cy="39.859219"
rx="3.7078164"
ry="3.0404093" /><ellipse
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:4.5;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="path829"
cx="57.174526"
cy="41.935596"
rx="1.7055955"
ry="2.0022209" /><path
style="fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
d="m 48.475092,62.720751 0.926955,2.940843 -1.325449,19.51173 3.034532,7.973073 2.71766,-8.101926 -2.573992,-19.420297 1.260658,-2.908793 -2.065856,-2.042716 z"
id="path831"
inkscape:connector-curvature="0"
sodipodi:nodetypes="ccccccccc" /></svg>

After

Width:  |  Height:  |  Size: 3.4 KiB

View File

@ -0,0 +1,61 @@
<?xml version="1.0" encoding="iso-8859-1"?>
<!-- Generator: Adobe Illustrator 19.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 512 512" style="enable-background:new 0 0 512 512;" xml:space="preserve">
<g>
<g>
<path d="M501.801,445.935h-18.359v-31.618c0-5.632-4.567-10.199-10.199-10.199h-10.08l-9.129-233.698l6.826-21.914h12.383
c5.632,0,10.199-4.567,10.199-10.199V115.48h12.239c4.897,0,9.102-3.479,10.019-8.289c0.916-4.81-1.713-9.592-6.266-11.394
L259.752,0.945c-2.41-0.955-5.094-0.955-7.506,0L12.565,95.798c-4.553,1.801-7.182,6.584-6.266,11.394
c0.917,4.81,5.122,8.289,10.019,8.289h12.239v22.827c0,5.632,4.566,10.199,10.199,10.199h12.383l6.826,21.912l-9.128,233.699
h-10.08c-5.633,0-10.199,4.567-10.199,10.199v31.617H10.199C4.566,445.934,0,450.501,0,456.133v45.438
c0,5.632,4.566,10.199,10.199,10.199h491.602c5.632,0,10.199-4.567,10.199-10.199v-45.438
C512,450.502,507.433,445.935,501.801,445.935z M48.956,128.109v-12.628h286.598c5.632,0,10.199-4.567,10.199-10.199
s-4.567-10.199-10.199-10.199H69.808L256,21.398l207.216,82.005l-0.172,24.706H48.956z M411.43,179.262h22.536l8.784,224.858
h-40.102L411.43,179.262z M405.901,148.508h33.594l-3.226,10.355h-27.142L405.901,148.508z M391.36,170.419l-9.128,233.699h-30.2
l-9.129-233.698l6.826-21.914h34.806L391.36,170.419z M300.298,179.262h22.536l8.784,224.858h-40.103L300.298,179.262z
M294.768,148.508h33.595l-3.226,10.355h-27.143L294.768,148.508z M231.771,170.419l6.826-21.912h34.806l6.826,21.914
L271.1,404.119h-30.201v-0.001L231.771,170.419z M189.167,179.262h22.536l8.784,224.858h-40.103L189.167,179.262z
M183.638,148.508h33.594l-3.226,10.355h-27.142L183.638,148.508z M169.099,170.419l-9.129,233.699h-30.201l-9.129-233.699
l6.826-21.912h34.807L169.099,170.419z M78.034,179.262h22.536l8.784,224.858H69.251L78.034,179.262z M72.505,148.507h33.594
l-3.226,10.355H75.731L72.505,148.507z M48.956,424.517h414.088v21.418H48.956V424.517z M491.602,491.374H20.398v-25.04h471.203
V491.374z"/>
</g>
</g>
<g>
<g>
<path d="M383.49,95.083h-9.179c-5.632,0-10.199,4.567-10.199,10.199c0,5.632,4.567,10.199,10.199,10.199h9.179
c5.632,0,10.199-4.567,10.199-10.199C393.689,99.65,389.122,95.083,383.49,95.083z"/>
</g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
<g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 2.5 KiB

View File

@ -0,0 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Svg Vector Icons : http://www.onlinewebfonts.com/icon -->
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 1000 1000" enable-background="new 0 0 1000 1000" xml:space="preserve">
<metadata> Svg Vector Icons : http://www.onlinewebfonts.com/icon </metadata>
<g><g transform="translate(0.000000,511.000000) scale(0.100000,-0.100000)"><path d="M1916.9,4475c-63.3-8.4-179.4-40.1-257.4-69.6c-386.2-145.6-664.7-436.8-810.3-846.2l-59.1-168.8l-6.3-1470.8l-6.3-1472.9h504.3c489.6,0,510.7,2.1,671.1,54.9C3265.4,938.3,4447.1,2540,4799.5,4356.9l27.4,141.4l-1397-2.1C2663.9,4494,1982.3,4485.6,1916.9,4475z"/><path d="M5202.6,4346.3c147.7-774.5,466.4-1553.1,905.3-2211.5c542.3-814.6,1236.6-1399.1,1939.3-1633.3c160.4-52.8,181.5-54.9,668.9-54.9h504.4v1388.5c-2.1,1470.8-6.3,1574.2-103.4,1814.8c-145.6,363-438.9,637.3-835.7,778.7l-168.8,59.1l-1468.7,6.3l-1470.8,6.3L5202.6,4346.3z"/><path d="M4917.7,1250.6c-16.9-10.6-88.6-194.2-160.4-407.3l-130.8-386.2l-413.6-10.6c-365.1-8.4-415.7-14.8-455.8-50.6c-48.5-44.3-59.1-135.1-16.9-185.7c12.7-16.9,164.6-135.1,337.6-257.4c170.9-124.5,310.2-227.9,310.2-230c0-2.1-52.8-164.6-116.1-362.9c-63.3-196.3-116.1-388.3-116.1-426.3c0-73.8,61.2-132.9,137.2-132.9c23.2,0,192,107.6,373.5,240.5l331.3,242.7l331.3-242.7c183.6-132.9,352.4-240.5,377.7-240.5c76,0,137.2,59.1,137.2,132.9c0,38-52.8,225.8-116.1,415.7S5612-296.2,5612-289.9c0,8.4,139.3,118.2,312.3,242.7c170.9,122.4,322.9,240.6,337.6,257.4c44.3,57,29.6,145.6-29.6,192c-52.8,42.2-84.4,44.3-460,44.3l-403.1,2.1l-116.1,360.9c-63.3,198.4-132.9,384.1-154,411.5C5059.1,1271.7,4972.6,1284.4,4917.7,1250.6z"/><path d="M779.5-1070.7v-1179.6l280.7-8.5c261.7-6.3,287-10.5,420-73.9c160.4-76,325-219.5,411.5-356.6c33.8-50.6,65.4-92.8,71.7-92.8c6.3,0,23.2,23.2,33.8,48.5c54.9,118.2,263.8,310.2,424.2,388.3c154.1,76,170.9,80.2,411.5,88.6l251.1,6.3l-14.8,109.7c-42.2,320.8-217.3,873.6-379.8,1194.4C2505.7-579,2197.6-199.2,1914.8,14l-126.6,94.9h-504.3H779.5V-1070.7z"/><path d="M8085.2,14c-287-215.3-595.1-599.3-780.8-970.7c-162.5-329.2-327.1-848.3-373.5-1183.9l-14.8-109.7l251.1-8.5c227.9-6.3,261.7-12.7,390.4-73.9c158.3-73.9,325-217.3,411.5-356.6c33.8-50.6,65.4-92.8,71.7-92.8c6.3,0,23.2,23.2,33.8,48.5c54.9,118.2,263.8,310.2,424.2,388.3c156.2,78.1,164.6,80.2,441,86.5l280.7,8.5v1179.6V108.9h-504.4h-504.3L8085.2,14z"/><path d="M593.8-2632.3c-137.2-48.6-280.7-181.5-352.4-329.2c-101.3-208.9-120.3-329.2-130.8-837.8L100-4280.4h848.3h848.3l-10.6,481.1c-10.5,510.7-29.6,628.9-130.8,839.9c-73.9,151.9-230,293.3-371.4,333.4C1123.5-2577.4,741.5-2581.6,593.8-2632.3z"/><path d="M2619.6-2632.3c-137.2-48.6-280.7-181.5-352.4-329.2c-101.3-208.9-120.3-329.2-130.8-837.8l-10.5-481.1h848.3h848.3l-10.6,481.1c-10.6,510.7-29.6,628.9-130.8,839.9c-73.9,151.9-230,293.3-371.4,333.4C3149.3-2577.4,2767.4-2581.6,2619.6-2632.3z"/><path d="M4645.5-2632.3c-204.7-69.6-379.8-299.6-447.4-582.4c-12.7-57-29.5-320.8-35.9-584.6l-10.6-481.1H5000h848.3l-10.5,481.1c-10.5,510.7-29.6,628.9-130.8,839.9c-73.9,151.9-230,293.3-371.4,333.4C5175.1-2577.4,4793.2-2581.6,4645.5-2632.3z"/><path d="M6671.3-2632.3c-137.2-48.6-280.7-181.5-352.4-329.2c-101.3-208.9-120.3-329.2-130.8-837.8l-10.5-481.1h848.3h848.3l-10.5,481.1c-10.6,510.7-29.6,628.9-130.8,839.9c-73.9,151.9-230,293.3-371.4,333.4C7201-2577.4,6819-2581.6,6671.3-2632.3z"/><path d="M8697.2-2632.3c-137.2-48.6-280.7-181.5-352.4-329.2c-101.3-208.9-120.3-329.2-130.8-837.8l-10.6-481.1h848.3H9900l-10.6,481.1c-10.5,510.7-29.6,628.9-130.8,839.9c-73.9,151.9-230,293.3-371.4,333.4C9226.8-2577.4,8844.9-2581.6,8697.2-2632.3z"/></g></g>
</svg>

After

Width:  |  Height:  |  Size: 3.6 KiB

View File

@ -0,0 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Svg Vector Icons : http://www.onlinewebfonts.com/icon -->
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 1000 1000" enable-background="new 0 0 1000 1000" xml:space="preserve">
<metadata> Svg Vector Icons : http://www.onlinewebfonts.com/icon </metadata>
<g><g><path d="M837.3,816.4c26.2,120.4-104.5,146.5-162.1,130.8c-57.6-15.7-175-18.3-175-18.3s-117.8,2.6-175.3,18.3c-57.6,15.8-188.4-10.4-162.3-130.8C188.7,696.1,303.9,701.3,335.4,539c31.5-162.3,164.9-151.8,164.9-151.8S633.4,376.7,664.9,539C696.2,701.3,811.2,696,837.3,816.4z M621,376.6c70.9,20.5,149.1-35.5,174.9-124.9c25.8-89.4-10.7-178.4-81.5-198.8c-70.9-20.5-149.1,35.5-174.9,124.9C513.7,267.1,550.2,356.2,621,376.6z M914.7,344.1c-68.2-27.9-152,19.4-187.2,105.6c-35.2,86.2-8.4,178.6,59.9,206.4c68.2,27.8,152-19.4,187.2-105.6C1009.7,464.2,982.9,371.9,914.7,344.1z M378.9,376.6c70.9-20.5,107.3-109.5,81.5-198.8C434.6,88.4,356.2,32.5,285.5,52.9C214.7,73.4,178.2,162.4,204,251.8C229.8,341.1,308,397.1,378.9,376.6z M212.7,656c68.2-27.9,95-120.3,59.9-206.4c-35.2-86.1-119-133.4-187.2-105.6c-68.2,27.9-95,120.3-59.9,206.4C60.6,636.6,144.4,683.9,212.7,656z"/></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g><g></g></g>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

View File

@ -0,0 +1,82 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="100"
height="100"
viewBox="0 0 100 100"
version="1.1"
id="svg857"
inkscape:version="0.92.4 5da689c313, 2019-01-14"
sodipodi:docname="type_tv-show.svg">
<defs
id="defs851" />
<sodipodi:namedview
id="base"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0.0"
inkscape:pageshadow="2"
inkscape:zoom="7.9195959"
inkscape:cx="43.300441"
inkscape:cy="51.246657"
inkscape:document-units="px"
inkscape:current-layer="layer1"
showgrid="true"
units="px"
inkscape:window-width="1918"
inkscape:window-height="1038"
inkscape:window-x="0"
inkscape:window-y="20"
inkscape:window-maximized="1">
<inkscape:grid
type="xygrid"
id="grid5105" />
</sodipodi:namedview>
<metadata
id="metadata854">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(0,-270.54167)">
<rect
style="fill:#ffffff;fill-opacity:1;stroke:#00001d;stroke-width:6.53200006;stroke-linecap:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke markers fill"
id="rect5107"
width="80"
height="55.000015"
x="10"
y="285.54166"
ry="5.0000134"
rx="5" />
<path
style="fill:none;stroke:#000000;stroke-width:7.70200014;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
d="m 24.873731,353.44586 h 50"
id="path5109"
inkscape:connector-curvature="0" />
<path
style="fill:none;stroke:#000000;stroke-width:4.5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
d="m 40,300.54167 v 20 l 20,-10 z"
id="path5111"
inkscape:connector-curvature="0"
sodipodi:nodetypes="cccc" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 2.6 KiB

61
back/karusic-back.iml Normal file
View File

@ -0,0 +1,61 @@
<?xml version="1.0" encoding="UTF-8"?>
<module org.jetbrains.idea.maven.project.MavenProjectsManager.isMavenModule="true" type="JAVA_MODULE" version="4">
<component name="NewModuleRootManager" LANGUAGE_LEVEL="JDK_14">
<output url="file://$MODULE_DIR$/out/maven/classes" />
<output-test url="file://$MODULE_DIR$/out/maven/test-classes" />
<content url="file://$MODULE_DIR$">
<sourceFolder url="file://$MODULE_DIR$/src" isTestSource="false" />
<sourceFolder url="file://$MODULE_DIR$/test/src" isTestSource="true" />
<excludeFolder url="file://$MODULE_DIR$/out/maven" />
</content>
<orderEntry type="inheritedJdk" />
<orderEntry type="sourceFolder" forTests="false" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.media:jersey-media-multipart:2.32" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.core:jersey-common:2.32" level="project" />
<orderEntry type="library" name="Maven: jakarta.annotation:jakarta.annotation-api:1.3.5" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.hk2:osgi-resource-locator:1.0.3" level="project" />
<orderEntry type="library" name="Maven: com.sun.activation:jakarta.activation:1.2.2" level="project" />
<orderEntry type="library" name="Maven: org.jvnet.mimepull:mimepull:1.9.13" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.inject:jersey-hk2:2.32" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.hk2:hk2-locator:2.6.1" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.hk2.external:aopalliance-repackaged:2.6.1" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.hk2:hk2-api:2.6.1" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.hk2:hk2-utils:2.6.1" level="project" />
<orderEntry type="library" name="Maven: org.javassist:javassist:3.25.0-GA" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.containers:jersey-container-grizzly2-http:2.32" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.hk2.external:jakarta.inject:2.6.1" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.grizzly:grizzly-http-server:2.4.4" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.grizzly:grizzly-http:2.4.4" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.grizzly:grizzly-framework:2.4.4" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.core:jersey-server:2.32" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.core:jersey-client:2.32" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.media:jersey-media-jaxb:2.32" level="project" />
<orderEntry type="library" name="Maven: jakarta.validation:jakarta.validation-api:2.0.2" level="project" />
<orderEntry type="library" name="Maven: jakarta.xml.bind:jakarta.xml.bind-api:2.3.3" level="project" />
<orderEntry type="library" name="Maven: jakarta.ws.rs:jakarta.ws.rs-api:2.1.6" level="project" />
<orderEntry type="library" name="Maven: javax.xml.bind:jaxb-api:2.3.1" level="project" />
<orderEntry type="library" name="Maven: javax.activation:javax.activation-api:1.2.0" level="project" />
<orderEntry type="library" name="Maven: javax.ws.rs:javax.ws.rs-api:2.1.1" level="project" />
<orderEntry type="library" name="Maven: com.sun.xml.bind:jaxb-impl:2.3.1" level="project" />
<orderEntry type="library" name="Maven: com.sun.istack:istack-commons-runtime:3.0.7" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: org.glassfish.jersey.test-framework.providers:jersey-test-framework-provider-grizzly2:2.32" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: jakarta.servlet:jakarta.servlet-api:4.0.3" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: org.glassfish.jersey.test-framework:jersey-test-framework-core:2.32" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: org.glassfish.jersey.containers:jersey-container-servlet-core:2.32" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: org.glassfish.jersey.containers:jersey-container-grizzly2-servlet:2.32" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: org.glassfish.jersey.containers:jersey-container-servlet:2.32" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: org.glassfish.grizzly:grizzly-http-servlet:2.4.4" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: junit:junit:4.12" level="project" />
<orderEntry type="library" scope="TEST" name="Maven: org.hamcrest:hamcrest-core:1.3" level="project" />
<orderEntry type="library" name="Maven: mysql:mysql-connector-java:5.1.45" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.media:jersey-media-json-jackson:2.32" level="project" />
<orderEntry type="library" name="Maven: org.glassfish.jersey.ext:jersey-entity-filtering:2.32" level="project" />
<orderEntry type="library" name="Maven: com.fasterxml.jackson.core:jackson-annotations:2.10.1" level="project" />
<orderEntry type="library" name="Maven: com.fasterxml.jackson.module:jackson-module-jaxb-annotations:2.10.1" level="project" />
<orderEntry type="library" name="Maven: jakarta.activation:jakarta.activation-api:1.2.1" level="project" />
<orderEntry type="library" name="Maven: com.fasterxml.jackson.core:jackson-databind:2.8.10" level="project" />
<orderEntry type="library" name="Maven: com.fasterxml.jackson.core:jackson-core:2.8.10" level="project" />
<orderEntry type="library" name="Maven: javax.servlet:javax.servlet-api:3.0.1" level="project" />
<orderEntry type="library" name="Maven: org.jetbrains:annotations:20.1.0" level="project" />
</component>
</module>

248
back/pom.xml Normal file
View File

@ -0,0 +1,248 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>kar</groupId>
<artifactId>karusic</artifactId>
<version>0.1.0</version>
<properties>
<jaxrs.version>2.1</jaxrs.version>
<jersey.version>2.32</jersey.version>
<jaxb.version>2.3.1</jaxb.version>
<istack.version>3.0.7</istack.version>
<maven.compiler.version>3.1</maven.compiler.version>
<maven.compiler.source>17</maven.compiler.source>
<maven.compiler.target>17</maven.compiler.target>
<maven.dependency.version>3.1.1</maven.dependency.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.glassfish.jersey</groupId>
<artifactId>jersey-bom</artifactId>
<version>${jersey.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<!-- https://mvnrepository.com/artifact/org.glassfish.jersey.media/jersey-media-multipart -->
<dependency>
<groupId>org.glassfish.jersey.media</groupId>
<artifactId>jersey-media-multipart</artifactId>
</dependency>
<dependency>
<groupId>org.glassfish.jersey.inject</groupId>
<artifactId>jersey-hk2</artifactId>
</dependency>
<dependency>
<groupId>org.glassfish.jersey.containers</groupId>
<artifactId>jersey-container-grizzly2-http</artifactId>
</dependency>
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>${jaxb.version}</version>
</dependency>
<dependency>
<groupId>javax.ws.rs</groupId>
<artifactId>javax.ws.rs-api</artifactId>
<version>2.1.1</version>
</dependency>
<dependency>
<groupId>com.sun.xml.bind</groupId>
<artifactId>jaxb-impl</artifactId>
<version>${jaxb.version}</version>
</dependency>
<dependency>
<groupId>com.sun.istack</groupId>
<artifactId>istack-commons-runtime</artifactId>
<version>${istack.version}</version>
</dependency>
<dependency>
<groupId>org.glassfish.jersey.test-framework.providers</groupId>
<artifactId>jersey-test-framework-provider-grizzly2</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.45</version>
</dependency>
<dependency>
<groupId>org.glassfish.jersey.media</groupId>
<artifactId>jersey-media-json-jackson</artifactId>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.8.10</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.0.1</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.jetbrains</groupId>
<artifactId>annotations</artifactId>
<version>RELEASE</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>com.nimbusds</groupId>
<artifactId>nimbus-jose-jwt</artifactId>
<version>9.22</version>
</dependency>
</dependencies>
<build>
<sourceDirectory>src</sourceDirectory>
<testSourceDirectory>test/src</testSourceDirectory>
<directory>${project.basedir}/out/maven/</directory>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>${maven.compiler.version}</version>
<configuration>
<source>${maven.compiler.source}</source>
<target>${maven.compiler.target}</target>
<!--<encoding>${project.build.sourceEncoding}</encoding>-->
</configuration>
</plugin>
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>exec-maven-plugin</artifactId>
<version>1.4.0</version>
<configuration>
<mainClass>io.scenarium.oauth.WebLauncher</mainClass>
</configuration>
</plugin>
<!-- Create the source bundle -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-source-plugin</artifactId>
<executions>
<execution>
<id>attach-sources</id>
<goals>
<goal>jar</goal>
</goals>
</execution>
</executions>
</plugin>
<!-- junit results -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>3.0.0-M5</version>
</plugin>
<plugin>
<artifactId>maven-assembly-plugin</artifactId>
<configuration>
<archive>
<manifest>
<mainClass>fully.qualified.MainClass</mainClass>
</manifest>
</archive>
<descriptorRefs>
<descriptorRef>jar-with-dependencies</descriptorRef>
</descriptorRefs>
</configuration>
</plugin>
<!-- Create coverage -->
<!--
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>0.8.5</version>
<executions>
<execution>
<goals>
<goal>prepare-agent</goal>
</goals>
</execution>
<execution>
<id>report</id>
<phase>test</phase>
<goals>
<goal>report</goal>
</goals>
</execution>
</executions>
</plugin>
-->
<!-- Java-doc generation for stand-alone site -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-javadoc-plugin</artifactId>
<version>3.2.0</version>
<configuration>
<show>private</show>
<nohelp>true</nohelp>
</configuration>
</plugin>
<!-- Check the style of the code -->
<!--
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-checkstyle-plugin</artifactId>
<version>3.1.0</version>
<configuration>
<configLocation>CheckStyle.xml</configLocation>
<consoleOutput>true</consoleOutput>
<failOnViolation>true</failOnViolation>
<failsOnError>true</failsOnError>
<includeTestSourceDirectory>true</includeTestSourceDirectory>
</configuration>
</plugin>
<plugin>
<groupId>net.revelc.code.formatter</groupId>
<artifactId>formatter-maven-plugin</artifactId>
<version>2.12.2</version>
<configuration>
<encoding>UTF-8</encoding>
<lineEnding>LF</lineEnding>
<configFile>Formatter.xml</configFile>
<directories>
<directory>src/</directory>
<directory>test/src</directory>
</directories>
<includes>
<include>**/*.java</include>
</includes>
<excludes>
<exclude>module-info.java</exclude>
</excludes>
</configuration>
<executions>
<execution>
<goals>
<goal>validate</goal>
</goals>
</execution>
</executions>
</plugin>
-->
</plugins>
</build>
<!-- Generate Java-docs As Part Of Project Reports -->
<reporting>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-javadoc-plugin</artifactId>
<version>3.2.0</version>
<configuration>
<show>public</show>
</configuration>
</plugin>
</plugins>
</reporting>
</project>

View File

@ -0,0 +1,17 @@
FROM bellsoft/liberica-openjdk-alpine:latest
ENV LANG=C.UTF-8
#ENV JAVA_HOME=/usr/lib/jvm/java-14-openjdk
#ENV JAVAFX_HOME=$JAVA_HOME
#ENV PATH=/usr/lib/jvm/java-14-openjdk/bin/:$PATH
#ENV JAVA_VERSION=14.0.2
RUN mkdir /application/
ADD karideo.jar /application/
WORKDIR /application/
EXPOSE 18080
CMD ["java", "-cp", "/application/karideo.jar", "org.kar.karideo.WebLauncher"]

View File

@ -0,0 +1,12 @@
version: '3'
services:
karideo_back_service_2:
build: .
restart: always
image: org.kar/karideo
container_name: org.kar.karideo
ports:
- 22080:18080
volumes:
- ./properties.txt:/application/properties.txt
- /workspace/data/karideo/media:/application/data

Binary file not shown.

View File

@ -0,0 +1,9 @@
org.kar.karideo.dataTmpFolder=/application/data/tmp
org.kar.karideo.dataTmpFolder=/application/data/media
org.kar.karideo.rest.oauth=http://192.168.1.156:21080/oauth/api/
org.kar.karideo.db.host=1992.156.1.156
org.kar.karideo.db.port=20306
org.kar.karideo.db.login=root
org.kar.karideo.db.port=klkhj456gkgtkhjgvkujfhjgkjhgsdfhb3467465fgdhdesfgh
org.kar.karideo.db.name=karideo
org.kar.karideo.address=http://0.0.0.0:18080/karideo/api/

View File

@ -0,0 +1,138 @@
package org.kar.karusic;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.kar.karusic.db.DBEntry;
import org.kar.karusic.model.User;
import org.kar.karusic.model.UserSmall;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
public class UserDB {
public UserDB() {
}
public static User getUsers(long userId) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT * FROM user WHERE id = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setLong(1, userId);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
User out = new User(rs);
entry.disconnect();
return out;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
return null;
}
public static User getUserOrCreate(long userId, String userLogin) {
User user = getUsers(userId);
if (user != null) {
/*
boolean blocked = false;
boolean removed = false;
if (user.email != userOAuth.email || user.login != userOAuth.login || user.blocked != blocked || user.removed != removed) {
updateUsersInfoFromOAuth(userOAuth.id, userOAuth.email, userOAuth.login, blocked, removed);
} else {
updateUsersConnectionTime(userOAuth.id);
}
return getUsers(userOAuth.id);
*/
return user;
}
createUsersInfoFromOAuth(userId, userLogin);
return getUsers(userId);
}
/*
private static void updateUsersConnectionTime(long userId) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "UPDATE `user` SET `lastConnection`=now(3) WHERE `id` = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setLong(1, userId);
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
}
private static void updateUsersInfoFromOAuth(long userId, String email, String login, boolean blocked, boolean removed) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "UPDATE `user` SET `login`=?, `email`=?, `lastConnection`=now(3), `blocked`=?, `removed`=? WHERE id = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setString(1, login);
ps.setString(2, email);
ps.setString(3, blocked ? "TRUE" : "FALSE");
ps.setString(4, removed ? "TRUE" : "FALSE");
ps.setLong(5, userId);
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
}
*/
private static void createUsersInfoFromOAuth(long userId, String login) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "INSERT INTO `user` (`id`, `login`, `lastConnection`, `admin`, `blocked`, `removed`) VALUE (?,?,now(3),'FALSE','FALSE','FALSE')";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setLong(1, userId);
ps.setString(2, login);
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
}
}

View File

@ -0,0 +1,137 @@
package org.kar.karusic;
import java.net.URI;
import javax.ws.rs.core.UriBuilder;
import org.glassfish.grizzly.http.server.HttpServer;
import org.glassfish.jersey.grizzly2.httpserver.GrizzlyHttpServerFactory;
import org.glassfish.jersey.jackson.JacksonFeature;
import org.glassfish.jersey.media.multipart.MultiPartFeature;
import org.glassfish.jersey.server.ResourceConfig;
import org.kar.karusic.api.DataResource;
import org.kar.karusic.api.Front;
import org.kar.karusic.api.HealthCheck;
import org.kar.karusic.api.SeasonResource;
import org.kar.karusic.api.SeriesResource;
import org.kar.karusic.api.TypeResource;
import org.kar.karusic.api.UniverseResource;
import org.kar.karusic.api.UserResource;
import org.kar.karusic.api.VideoResource;
import org.kar.karusic.db.DBConfig;
import org.kar.karusic.filter.AuthenticationFilter;
import org.kar.karusic.filter.CORSFilter;
import org.kar.karusic.filter.OptionFilter;
import org.kar.karusic.model.Album;
import org.kar.karusic.model.Artist;
import org.kar.karusic.model.DataSmall;
import org.kar.karusic.model.Gender;
import org.kar.karusic.model.Playlist;
import org.kar.karusic.model.Track;
import org.kar.karusic.model.User;
import org.kar.karusic.util.ConfigVariable;
import org.kar.karusic.util.JWTWrapper;
public class WebLauncher {
public static DBConfig dbConfig;
private WebLauncher() {
}
private static URI getBaseURI() {
return UriBuilder.fromUri(ConfigVariable.getlocalAddress()).build();
}
public static void main(String[] args) {
if (true) {
// generate the BDD:
String out = "";
out += new DataSmall().getTableSql();
out += new User().getTableSql();
out += new Track().getTableSql();
out += new Artist().getTableSql();
out += new Gender().getTableSql();
out += new Playlist().getTableSql();
out += new Album().getTableSql();
System.out.println(out);
return;
}
ResourceConfig rc = new ResourceConfig();
// need to uppgrade when server call us...
try {
JWTWrapper.initLocalTokenRemote(ConfigVariable.getSSOAddress(), "karusic");
} catch (Exception e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
System.out.println("Wait 10 seconds ....");
try {
Thread.sleep(10000);
} catch (InterruptedException e) {
e.printStackTrace();
}
return;
}
// add multipart models ..
//rc.register(new MultiPartFeature());
//rc.register(new InjectionBinder());
rc.register(new MultiPartFeature());
//rc.register(new MyFileUploader());
// global authentication system
rc.register(new OptionFilter());
// remove cors ==> all time called by an other system...
rc.register(new CORSFilter());
// global authentication system
//rc.register(new AuthenticationFilter());
rc.registerClasses(AuthenticationFilter.class);
// add default resource:
rc.registerClasses(UserResource.class);
rc.registerClasses(SeriesResource.class);
rc.registerClasses(DataResource.class);
rc.registerClasses(SeasonResource.class);
rc.registerClasses(TypeResource.class);
rc.registerClasses(UniverseResource.class);
rc.registerClasses(VideoResource.class);
rc.registerClasses(HealthCheck.class);
rc.registerClasses(Front.class);
// add jackson to be discovenr when we are ins standalone server
rc.register(JacksonFeature.class);
// enable this to show low level request
//rc.property(LoggingFeature.LOGGING_FEATURE_LOGGER_LEVEL_SERVER, Level.WARNING.getName());
//System.out.println("Connect on the BDD:");
//System.out.println(" getDBHost: '" + ConfigVariable.getDBHost() + "'");
//System.out.println(" getDBPort: '" + ConfigVariable.getDBPort() + "'");
//System.out.println(" getDBLogin: '" + ConfigVariable.getDBLogin() + "'");
//System.out.println(" getDBPassword: '" + ConfigVariable.getDBPassword() + "'");
//System.out.println(" getDBName: '" + ConfigVariable.getDBName() + "'");
dbConfig = new DBConfig(ConfigVariable.getDBHost(),
Integer.parseInt(ConfigVariable.getDBPort()),
ConfigVariable.getDBLogin(),
ConfigVariable.getDBPassword(),
ConfigVariable.getDBName());
System.out.println(" ==> " + dbConfig);
System.out.println("OAuth service " + getBaseURI());
HttpServer server = GrizzlyHttpServerFactory.createHttpServer(getBaseURI(), rc);
Runtime.getRuntime().addShutdownHook(new Thread(new Runnable() {
@Override
public void run() {
System.out.println("Stopping server..");
server.shutdownNow();
}
}, "shutdownHook"));
// run
try {
server.start();
System.out.println("Jersey app started at " + getBaseURI());
System.out.println("Press CTRL^C to exit..");
Thread.currentThread().join();
} catch (Exception e) {
System.out.println("There was an error while starting Grizzly HTTP server.");
e.printStackTrace();
}
}
}

View File

@ -0,0 +1,15 @@
package org.kar.karusic.annotation;
import javax.ws.rs.NameBinding;
import java.lang.annotation.Retention;
import java.lang.annotation.Target;
import static java.lang.annotation.ElementType.METHOD;
import static java.lang.annotation.ElementType.TYPE;
import static java.lang.annotation.RetentionPolicy.RUNTIME;
@NameBinding
@Retention(RUNTIME)
@Target({METHOD})
public @interface PermitTokenInURI {
}

View File

@ -0,0 +1,515 @@
package org.kar.karusic.api;
import org.glassfish.jersey.media.multipart.FormDataContentDisposition;
import org.glassfish.jersey.media.multipart.FormDataParam;
import org.kar.karusic.WebLauncher;
import org.kar.karusic.annotation.PermitTokenInURI;
import org.kar.karusic.db.DBEntry;
import org.kar.karusic.filter.GenericContext;
import org.kar.karusic.model.Data;
import org.kar.karusic.model.DataSmall;
import org.kar.karusic.util.ConfigVariable;
import javax.annotation.security.PermitAll;
import javax.annotation.security.RolesAllowed;
import javax.imageio.ImageIO;
import javax.ws.rs.*;
import javax.ws.rs.core.CacheControl;
import javax.ws.rs.core.Context;
import javax.ws.rs.core.HttpHeaders;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.SecurityContext;
import javax.ws.rs.core.StreamingOutput;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.*;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Date;
import java.util.concurrent.TimeUnit;
// https://stackoverflow.com/questions/35367113/jersey-webservice-scalable-approach-to-download-file-and-reply-to-client
// https://gist.github.com/aitoroses/4f7a2b197b732a6a691d
@Path("/data")
@Produces({MediaType.APPLICATION_JSON})
public class DataResource {
private final static int CHUNK_SIZE = 1024 * 1024; // 1MB chunks
private final static int CHUNK_SIZE_IN = 50 * 1024 * 1024; // 1MB chunks
/**
* Upload some datas
*/
private static long tmpFolderId = 1;
private static void createFolder(String path) throws IOException {
if (!Files.exists(java.nio.file.Path.of(path))) {
//Log.print("Create folder: " + path);
Files.createDirectories(java.nio.file.Path.of(path));
}
}
public static long getTmpDataId() {
return tmpFolderId++;
}
public static String getTmpFileInData(long tmpFolderId) {
String filePath = ConfigVariable.getTmpDataFolder() + File.separator + tmpFolderId;
try {
createFolder(ConfigVariable.getTmpDataFolder() + File.separator);
} catch (IOException e) {
e.printStackTrace();
}
return filePath;
}
public static String getFileData(long tmpFolderId) {
String filePath = ConfigVariable.getMediaDataFolder() + File.separator + tmpFolderId + File.separator + "data";
try {
createFolder(ConfigVariable.getMediaDataFolder() + File.separator + tmpFolderId + File.separator);
} catch (IOException e) {
e.printStackTrace();
}
return filePath;
}
public static Data getWithSha512(String sha512) {
System.out.println("find sha512 = " + sha512);
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT `id`, `deleted`, `sha512`, `mime_type`, `size` FROM `data` WHERE `sha512` = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setString(1, sha512);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
Data out = new Data(rs);
entry.disconnect();
return out;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
return null;
}
public static Data getWithId(long id) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT `id`, `deleted`, `sha512`, `mime_type`, `size` FROM `data` WHERE `deleted` = false AND `id` = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setLong(1, id);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
Data out = new Data(rs);
entry.disconnect();
return out;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
return null;
}
public static Data createNewData(long tmpUID, String originalFileName, String sha512) throws IOException, SQLException {
// determine mime type:
String mimeType = "";
String extension = originalFileName.substring(originalFileName.lastIndexOf('.') + 1);
switch (extension.toLowerCase()) {
case "jpg":
case "jpeg":
mimeType = "image/jpeg";
break;
case "png":
mimeType = "image/png";
break;
case "webp":
mimeType = "image/webp";
break;
case "mka":
mimeType = "audio/x-matroska";
break;
case "mkv":
mimeType = "video/x-matroska";
break;
case "webm":
mimeType = "video/webm";
break;
default:
throw new IOException("Can not find the mime type of data input: '" + extension + "'");
}
String tmpPath = getTmpFileInData(tmpUID);
long fileSize = Files.size(Paths.get(tmpPath));
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
long uniqueSQLID = -1;
try {
// prepare the request:
String query = "INSERT INTO `data` (`sha512`, `mime_type`, `size`, `original_name`) VALUES (?, ?, ?, ?)";
PreparedStatement ps = entry.connection.prepareStatement(query,
Statement.RETURN_GENERATED_KEYS);
int iii = 1;
ps.setString(iii++, sha512);
ps.setString(iii++, mimeType);
ps.setLong(iii++, fileSize);
ps.setString(iii++, originalFileName);
// execute the request
int affectedRows = ps.executeUpdate();
if (affectedRows == 0) {
throw new SQLException("Creating data failed, no rows affected.");
}
// retreive uid inserted
try (ResultSet generatedKeys = ps.getGeneratedKeys()) {
if (generatedKeys.next()) {
uniqueSQLID = generatedKeys.getLong(1);
} else {
throw new SQLException("Creating user failed, no ID obtained (1).");
}
} catch (Exception ex) {
System.out.println("Can not get the UID key inserted ... ");
ex.printStackTrace();
throw new SQLException("Creating user failed, no ID obtained (2).");
}
} catch (SQLException ex) {
ex.printStackTrace();
}
entry.disconnect();
System.out.println("Add Data raw done. uid data=" + uniqueSQLID);
Data out = getWithId(uniqueSQLID);
String mediaPath = getFileData(out.id);
System.out.println("src = " + tmpPath);
System.out.println("dst = " + mediaPath);
Files.move(Paths.get(tmpPath), Paths.get(mediaPath), StandardCopyOption.ATOMIC_MOVE);
System.out.println("Move done");
// all is done the file is corectly installed...
return out;
}
public static void undelete(Long id) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "UPDATE `data` SET `deleted` = false WHERE `id` = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setLong(1, id);
ps.execute();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
}
static String saveTemporaryFile(InputStream uploadedInputStream, long idData) {
return saveFile(uploadedInputStream, DataResource.getTmpFileInData(idData));
}
static void removeTemporaryFile(long idData) {
String filepath = DataResource.getTmpFileInData(idData);
if (Files.exists(Paths.get(filepath))) {
try {
Files.delete(Paths.get(filepath));
} catch (IOException e) {
System.out.println("can not delete temporary file : " + Paths.get(filepath));
e.printStackTrace();
}
}
}
// save uploaded file to a defined location on the server
static String saveFile(InputStream uploadedInputStream, String serverLocation) {
String out = "";
try {
OutputStream outpuStream = new FileOutputStream(new File(
serverLocation));
int read = 0;
byte[] bytes = new byte[CHUNK_SIZE_IN];
MessageDigest md = MessageDigest.getInstance("SHA-512");
outpuStream = new FileOutputStream(new File(serverLocation));
while ((read = uploadedInputStream.read(bytes)) != -1) {
//System.out.println("write " + read);
md.update(bytes, 0, read);
outpuStream.write(bytes, 0, read);
}
System.out.println("Flush input stream ... " + serverLocation);
System.out.flush();
outpuStream.flush();
outpuStream.close();
// create the end of sha512
byte[] sha512Digest = md.digest();
// convert in hexadecimal
out = bytesToHex(sha512Digest);
uploadedInputStream.close();
} catch (IOException ex) {
System.out.println("Can not write in temporary file ... ");
ex.printStackTrace();
} catch (NoSuchAlgorithmException ex) {
System.out.println("Can not find sha512 algorithms");
ex.printStackTrace();
}
return out;
}
// curl http://localhost:9993/api/users/3
//@Secured
/*
@GET
@Path("{id}")
//@RolesAllowed("GUEST")
@Produces(MediaType.APPLICATION_OCTET_STREAM)
public Response retriveData(@HeaderParam("Range") String range, @PathParam("id") Long id) throws Exception {
return retriveDataFull(range, id, "no-name");
}
*/
public static String bytesToHex(byte[] bytes) {
StringBuilder sb = new StringBuilder();
for (byte b : bytes) {
sb.append(String.format("%02x", b));
}
return sb.toString();
}
/*
@POST
@Path("/upload")
@Consumes(MediaType.MULTIPART_FORM_DATA)
public Response uploadFile(FormDataMultiPart form) {
FormDataBodyPart filePart = form.getField("file");
ContentDisposition headerOfFilePart = filePart.getContentDisposition();
InputStream fileInputStream = filePart.getValueAs(InputStream.class);
String filePath = ConfigVariable.getTmpDataFolder() + File.separator + tmpFolderId++;
//headerOfFilePart.getFileName();
// save the file to the server
saveFile(fileInputStream, filePath);
String output = "File saved to server location using FormDataMultiPart : " + filePath;
return Response.status(200).entity(output).build();
}
*/
public DataSmall getSmall(Long id) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT `id`, `sha512`, `mime_type`, `size` FROM `data` WHERE `deleted` = false AND `id` = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setLong(1, id);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
DataSmall out = new DataSmall(rs);
entry.disconnect();
return out;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
return null;
}
@POST
@Path("/upload/")
@Consumes({MediaType.MULTIPART_FORM_DATA})
@RolesAllowed("ADMIN")
public Response uploadFile(@Context SecurityContext sc, @FormDataParam("file") InputStream fileInputStream, @FormDataParam("file") FormDataContentDisposition fileMetaData) {
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("===================================================");
System.out.println("== DATA uploadFile " + (gc==null?"null":gc.user));
System.out.println("===================================================");
//public NodeSmall uploadFile(final FormDataMultiPart form) {
System.out.println("Upload file: ");
String filePath = ConfigVariable.getTmpDataFolder() + File.separator + tmpFolderId++;
try {
createFolder(ConfigVariable.getTmpDataFolder() + File.separator);
} catch (IOException e) {
e.printStackTrace();
}
saveFile(fileInputStream, filePath);
return Response.ok("Data uploaded successfully !!").build();
//return null;
}
@GET
@Path("{id}")
@PermitTokenInURI
@RolesAllowed("USER")
@Produces(MediaType.APPLICATION_OCTET_STREAM)
public Response retriveDataId(@Context SecurityContext sc, @QueryParam(HttpHeaders.AUTHORIZATION) String token, @HeaderParam("Range") String range, @PathParam("id") Long id) throws Exception {
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("===================================================");
System.out.println("== DATA retriveDataId ? " + (gc==null?"null":gc.user));
System.out.println("===================================================");
DataSmall value = getSmall(id);
if (value == null) {
Response.status(404).
entity("media NOT FOUND: " + id).
type("text/plain").
build();
}
return buildStream(ConfigVariable.getMediaDataFolder() + File.separator + id + File.separator + "data", range, value.mimeType);
}
@GET
@Path("thumbnail/{id}")
@RolesAllowed("USER")
@PermitTokenInURI
@Produces(MediaType.APPLICATION_OCTET_STREAM)
//@CacheMaxAge(time = 10, unit = TimeUnit.DAYS)
public Response retriveDataThumbnailId(@Context SecurityContext sc, @QueryParam(HttpHeaders.AUTHORIZATION) String token, @HeaderParam("Range") String range, @PathParam("id") Long id) throws Exception {
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("===================================================");
System.out.println("== DATA retriveDataThumbnailId ? " + (gc==null?"null":gc.user));
System.out.println("===================================================");
DataSmall value = getSmall(id);
if (value == null) {
return Response.status(404).
entity("media NOT FOUND: " + id).
type("text/plain").
build();
}
String filePathName = ConfigVariable.getMediaDataFolder() + File.separator + id + File.separator + "data";
if ( value.mimeType.contentEquals("image/jpeg")
|| value.mimeType.contentEquals("image/png")
// || value.mimeType.contentEquals("image/webp")
) {
// reads input image
File inputFile = new File(filePathName);
BufferedImage inputImage = ImageIO.read(inputFile);
int scaledWidth = 250;
int scaledHeight = (int)((float)inputImage.getHeight() / (float)inputImage.getWidth() * (float) scaledWidth);
// creates output image
BufferedImage outputImage = new BufferedImage(scaledWidth,
scaledHeight, inputImage.getType());
// scales the input image to the output image
Graphics2D g2d = outputImage.createGraphics();
g2d.drawImage(inputImage, 0, 0, scaledWidth, scaledHeight, null);
g2d.dispose();
// create the oputput stream:
ByteArrayOutputStream baos = new ByteArrayOutputStream();
ImageIO.write(outputImage, "JPG", baos);
byte[] imageData = baos.toByteArray();
Response.ok(new ByteArrayInputStream(imageData)).build();
Response.ResponseBuilder out = Response.ok(imageData)
.header(HttpHeaders.CONTENT_LENGTH, imageData.length);
out.type("image/jpeg");
return out.build();
}
return buildStream(filePathName, range, value.mimeType);
}
//@Secured
@GET
@Path("{id}/{name}")
@PermitTokenInURI
//@RolesAllowed("USER")
@PermitAll
@Produces(MediaType.APPLICATION_OCTET_STREAM)
public Response retriveDataFull(@Context SecurityContext sc, @QueryParam(HttpHeaders.AUTHORIZATION) String token, @HeaderParam("Range") String range, @PathParam("id") Long id, @PathParam("name") String name) throws Exception {
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("===================================================");
System.out.println("== DATA retriveDataFull ? " + (gc==null?"null":gc.user));
System.out.println("===================================================");
DataSmall value = getSmall(id);
if (value == null) {
Response.status(404).
entity("media NOT FOUND: " + id).
type("text/plain").
build();
}
return buildStream(ConfigVariable.getMediaDataFolder() + File.separator + id + File.separator + "data", range, value.mimeType);
}
/**
* Adapted from http://stackoverflow.com/questions/12768812/video-streaming-to-ipad-does-not-work-with-tapestry5/12829541#12829541
*
* @param range range header
* @return Streaming output
* @throws Exception IOException if an error occurs in streaming.
*/
private Response buildStream(final String filename, final String range, String mimeType) throws Exception {
File file = new File(filename);
//System.out.println("request range : " + range);
// range not requested : Firefox does not send range headers
if (range == null) {
final StreamingOutput output = new StreamingOutput() {
@Override
public void write(OutputStream out) {
try (FileInputStream in = new FileInputStream(file)) {
byte[] buf = new byte[1024 * 1024];
int len;
while ((len = in.read(buf)) != -1) {
try {
out.write(buf, 0, len);
out.flush();
//System.out.println("---- wrote " + len + " bytes file ----");
} catch (IOException ex) {
System.out.println("remote close connection");
break;
}
}
} catch (IOException ex) {
throw new InternalServerErrorException(ex);
}
}
};
Response.ResponseBuilder out = Response.ok(output)
.header(HttpHeaders.CONTENT_LENGTH, file.length());
if (mimeType != null) {
out.type(mimeType);
}
return out.build();
}
String[] ranges = range.split("=")[1].split("-");
final long from = Long.parseLong(ranges[0]);
//System.out.println("request range : " + ranges.length);
//Chunk media if the range upper bound is unspecified. Chrome, Opera sends "bytes=0-"
long to = CHUNK_SIZE + from;
if (ranges.length == 1) {
to = file.length() - 1;
} else {
if (to >= file.length()) {
to = (long) (file.length() - 1);
}
}
final String responseRange = String.format("bytes %d-%d/%d", from, to, file.length());
//System.out.println("responseRange : " + responseRange);
final RandomAccessFile raf = new RandomAccessFile(file, "r");
raf.seek(from);
final long len = to - from + 1;
final MediaStreamer streamer = new MediaStreamer(len, raf);
Response.ResponseBuilder out = Response.ok(streamer)
.status(Response.Status.PARTIAL_CONTENT)
.header("Accept-Ranges", "bytes")
.header("Content-Range", responseRange)
.header(HttpHeaders.CONTENT_LENGTH, streamer.getLenth())
.header(HttpHeaders.LAST_MODIFIED, new Date(file.lastModified()));
if (mimeType != null) {
out.type(mimeType);
}
return out.build();
}
}

View File

@ -0,0 +1,103 @@
package org.kar.karusic.api;
import java.io.File;
import java.util.List;
import javax.annotation.security.PermitAll;
import javax.ws.rs.*;
import javax.ws.rs.core.CacheControl;
import javax.ws.rs.core.PathSegment;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.Response.ResponseBuilder;
import org.kar.karusic.util.ConfigVariable;
@Path("/karusic")
public class Front {
private String getExtension(String filename) {
if (filename.contains(".")) {
return filename.substring(filename.lastIndexOf(".") + 1);
}
return "";
}
private Response retrive(String fileName) throws Exception {
String filePathName = ConfigVariable.getFrontFolder() + File.separator + fileName;
String extention = getExtension(filePathName);
String mineType = null;
System.out.println("try retrive : '" + filePathName + "' '" + extention + "'");
if (extention.length() !=0 && extention.length() <= 5) {
if (extention.equalsIgnoreCase("jpg") || extention.equalsIgnoreCase("jpeg")) {
mineType = "image/jpeg";
} else if (extention.equalsIgnoreCase("gif")) {
mineType = "image/gif";
} else if (extention.equalsIgnoreCase("png")) {
mineType = "image/png";
} else if (extention.equalsIgnoreCase("svg")) {
mineType = "image/svg+xml";
} else if (extention.equalsIgnoreCase("webp")) {
mineType = "image/webp";
} else if (extention.equalsIgnoreCase("js")) {
mineType = "application/javascript";
} else if (extention.equalsIgnoreCase("json")) {
mineType = "application/json";
} else if (extention.equalsIgnoreCase("ico")) {
mineType = "image/x-icon";
} else if (extention.equalsIgnoreCase("html")) {
mineType = "text/html";
} else if (extention.equalsIgnoreCase("css")) {
mineType = "text/css";
} else {
return Response.status(403).
entity("Not supported model: '" + fileName + "'").
type("text/plain").
build();
}
} else {
mineType = "text/html";
filePathName = ConfigVariable.getFrontFolder() + File.separator + "index.html";
}
System.out.println(" ==> '" + filePathName + "'");
// reads input image
File download = new File(filePathName);
if (!download.exists()) {
return Response.status(404).
entity("Not Found: '" + fileName + "' extension='" + extention + "'").
type("text/plain").
build();
}
ResponseBuilder response = Response.ok((Object)download);
// use this if I want to download the file:
//response.header("Content-Disposition", "attachment; filename=" + fileName);
CacheControl cc = new CacheControl();
cc.setMaxAge(60);
cc.setNoCache(false);
response.cacheControl(cc);
response.type(mineType);
return response.build();
}
@GET
@PermitAll()
//@Produces(MediaType.APPLICATION_OCTET_STREAM)
//@CacheMaxAge(time = 1, unit = TimeUnit.DAYS)
public Response retrive0() throws Exception {
return retrive("index.html");
}
@GET
@Path("{any: .*}")
@PermitAll()
//@Produces(MediaType.APPLICATION_OCTET_STREAM)
//@CacheMaxAge(time = 10, unit = TimeUnit.DAYS)
public Response retrive1(@PathParam("any") List<PathSegment> segments) throws Exception {
String filename = "";
for (PathSegment elem: segments) {
if (!filename.isEmpty()) {
filename += File.separator;
}
filename += elem.getPath();
}
return retrive(filename);
}
}

View File

@ -0,0 +1,22 @@
package org.kar.karusic.api;
import javax.annotation.security.PermitAll;
import javax.ws.rs.*;
import javax.ws.rs.core.MediaType;
@Path("/health_check")
@Produces(MediaType.APPLICATION_JSON)
public class HealthCheck {
public class HealthResult {
public String value;
public HealthResult(String value) {
this.value = value;
}
}
// todo : do it better...
@GET
@PermitAll
public HealthResult getHealth() {
return new HealthResult("alive and kicking");
}
}

View File

@ -0,0 +1,71 @@
package org.kar.karusic.api;
import javax.ws.rs.InternalServerErrorException;
import javax.ws.rs.WebApplicationException;
import javax.ws.rs.core.StreamingOutput;
import java.io.IOException;
import java.io.OutputStream;
import java.io.RandomAccessFile;
public class MediaStreamer implements StreamingOutput {
private final int CHUNK_SIZE = 1024 * 1024; // 1MB chunks
final byte[] buf = new byte[CHUNK_SIZE];
private long length;
private RandomAccessFile raf;
public MediaStreamer(long length, RandomAccessFile raf) throws IOException {
//System.out.println("request stream of " + length / 1024 + " data");
if (length<0) {
throw new IOException("Wrong size of the file to stream: " + length);
}
this.length = length;
this.raf = raf;
}
/*
public void write(OutputStream out) {
try (FileInputStream in = new FileInputStream(file)) {
byte[] buf = new byte[1024*1024];
int len;
while ((len = in.read(buf)) != -1) {
out.write(buf, 0, len);
out.flush();
//System.out.println("---- wrote " + len + " bytes file ----");
}
} catch (IOException ex) {
throw new InternalServerErrorException(ex);
}
}
*/
@Override
public void write(OutputStream outputStream) {
try {
while (length != 0) {
int read = raf.read(buf, 0, buf.length > length ? (int) length : buf.length);
try {
outputStream.write(buf, 0, read);
} catch (IOException ex) {
System.out.println("remote close connection");
break;
}
length -= read;
}
} catch (IOException ex) {
throw new InternalServerErrorException(ex);
} catch (WebApplicationException ex) {
throw new InternalServerErrorException(ex);
} finally {
try {
raf.close();
} catch (IOException ex) {
ex.printStackTrace();
throw new InternalServerErrorException(ex);
}
}
}
public long getLenth() {
return length;
}
}

View File

@ -0,0 +1,482 @@
package org.kar.karusic.api;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.glassfish.jersey.media.multipart.FormDataContentDisposition;
import org.kar.karusic.WebLauncher;
import org.kar.karusic.db.DBEntry;
import org.kar.karusic.model.Data;
import org.kar.karusic.model.NodeSmall;
import javax.ws.rs.core.Response;
import java.io.IOException;
import java.io.InputStream;
import java.sql.*;
import java.util.ArrayList;
import java.util.List;
public class NodeInterface {
/* test en SQL qui fait joli...
SELECT node.id,
node.name,
node.description,
node.parent_id,
GROUP_CONCAT(cover_link_node.data_id SEPARATOR '-') as covers
FROM node, cover_link_node
WHERE node.deleted = false AND cover_link_node.deleted = false AND node.type = "TYPE" AND cover_link_node.node_id = node.id
GROUP BY node.id
ORDER BY node.name
// bon c'est bien mais c'est mieux en faisant un left join avec préfiltrage ...
SELECT node.id,
node.name,
node.description,
node.parent_id,
cover_link_node.data_id
FROM node
LEFT JOIN cover_link_node
ON node.id = cover_link_node.node_id
AND cover_link_node.deleted = false
WHERE node.deleted = false
AND node.type = "TYPE"
ORDER BY node.name
// marche pas:
SELECT node.id,
node.name,
node.description,
node.parent_id,
`extract.covers`
FROM node
LEFT JOIN (SELECT tmp.node_id,
GROUP_CONCAT(`tmp.data_id` SEPARATOR '-') as `covers`
FROM cover_link_node tmp
WHERE tmp.deleted = false
GROUP BY tmp.node_id) extract
ON node.id = extract.node_id
WHERE node.deleted = false
AND node.type = "TYPE"
ORDER BY node.name
// et enfin une version qui fonctionne ...
SELECT node.id,
node.name,
node.description,
node.parent_id,
(SELECT GROUP_CONCAT(tmp.data_id)
FROM cover_link_node tmp
WHERE tmp.deleted = false
AND node.id = tmp.node_id
GROUP BY tmp.node_id) AS covers
FROM node
WHERE node.deleted = false
AND node.type = "TYPE"
ORDER BY node.name
*/
public static List<NodeSmall> get(String typeInNode) {
System.out.println(typeInNode + " get");
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
List<NodeSmall> out = new ArrayList<>();
String query = "SELECT node.id," +
" node.name," +
" node.description," +
" node.parent_id," +
" (SELECT GROUP_CONCAT(tmp.data_id SEPARATOR '-')" +
" FROM cover_link_node tmp" +
" WHERE tmp.deleted = false" +
" AND node.id = tmp.node_id" +
" GROUP BY tmp.node_id) AS covers" +
" FROM node" +
" WHERE node.deleted = false " +
" AND node.type = ?" +
" ORDER BY node.name";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setString(iii++, typeInNode);
ResultSet rs = ps.executeQuery();
while (rs.next()) {
out.add(new NodeSmall(rs));
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
entry = null;
System.out.println("retrieve " + out.size() + " " + typeInNode);
return out;
}
public static NodeSmall getWithId(String typeInNode, long id) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT node.id," +
" node.name," +
" node.description," +
" node.parent_id," +
" (SELECT GROUP_CONCAT(tmp.data_id SEPARATOR '-')" +
" FROM cover_link_node tmp" +
" WHERE tmp.deleted = false" +
" AND node.id = tmp.node_id" +
" GROUP BY tmp.node_id) AS covers" +
" FROM node" +
" WHERE node.deleted = false " +
" AND node.type = ?" +
" AND node.id = ?" +
" ORDER BY node.name";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setString(iii++, typeInNode);
ps.setLong(iii++, id);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
NodeSmall out = new NodeSmall(rs);
entry.disconnect();
entry = null;
return out;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
entry = null;
return null;
}
public static List<NodeSmall> getWithName(String typeInNode, String name) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
List<NodeSmall> out = new ArrayList<>();
String query = "SELECT node.id," +
" node.name," +
" node.description," +
" node.parent_id," +
" (SELECT GROUP_CONCAT(tmp.data_id SEPARATOR '-')" +
" FROM cover_link_node tmp" +
" WHERE tmp.deleted = false" +
" AND node.id = tmp.node_id" +
" GROUP BY tmp.node_id) AS covers" +
" FROM node" +
" WHERE node.deleted = false " +
" AND node.type = ?" +
" AND node.name = ?" +
" ORDER BY node.name";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setString(iii++, typeInNode);
ps.setString(iii++, name);
ResultSet rs = ps.executeQuery();
while (rs.next()) {
out.add(new NodeSmall(rs));
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
entry = null;
return out;
}
public static NodeSmall getWithNameAndParent(String typeInNode, String name, long parentId) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT node.id," +
" node.name," +
" node.description," +
" node.parent_id," +
" (SELECT GROUP_CONCAT(tmp.data_id SEPARATOR '-')" +
" FROM cover_link_node tmp" +
" WHERE tmp.deleted = false" +
" AND node.id = tmp.node_id" +
" GROUP BY tmp.node_id) AS covers" +
" FROM node" +
" WHERE node.deleted = false " +
" AND node.type = ?" +
" AND node.name = ?" +
" AND node.parent_id = ?" +
" ORDER BY node.name";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setString(iii++, typeInNode);
ps.setString(iii++, name);
ps.setLong(iii++, parentId);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
NodeSmall out = new NodeSmall(rs);
entry.disconnect();
entry = null;
return out;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
entry = null;
return null;
}
public static NodeSmall createNode(String typeInNode, String name, String descrition, Long parentId) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
long uniqueSQLID = -1;
// real add in the BDD:
try {
// prepare the request:
String query = "INSERT INTO node (`type`, `name`, `description`, `parent_id`) VALUES (?, ?, ?, ?)";
PreparedStatement ps = entry.connection.prepareStatement(query,
Statement.RETURN_GENERATED_KEYS);
int iii = 1;
ps.setString(iii++, typeInNode);
ps.setString(iii++, name);
if (descrition == null) {
ps.setNull(iii++, Types.VARCHAR);
} else {
ps.setString(iii++, descrition);
}
if (parentId == null) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, parentId);
}
// execute the request
int affectedRows = ps.executeUpdate();
if (affectedRows == 0) {
throw new SQLException("Creating node failed, no rows affected.");
}
// retreive uid inserted
try (ResultSet generatedKeys = ps.getGeneratedKeys()) {
if (generatedKeys.next()) {
uniqueSQLID = generatedKeys.getLong(1);
} else {
throw new SQLException("Creating node failed, no ID obtained (1).");
}
} catch (Exception ex) {
System.out.println("Can not get the UID key inserted ... ");
ex.printStackTrace();
throw new SQLException("Creating node failed, no ID obtained (2).");
}
//ps.execute();
} catch (SQLException ex) {
ex.printStackTrace();
}
return getWithId(typeInNode, uniqueSQLID);
}
public static NodeSmall getOrCreate(String typeInNode, String name, Long parentId) {
if (name == null || name.isEmpty()) {
return null;
}
NodeSmall node = getWithNameAndParent(typeInNode, name, parentId);
if (node != null) {
return node;
}
return createNode(typeInNode, name, null, parentId);
}
static private String multipartCorrection(String data) {
if (data == null) {
return null;
}
if (data.isEmpty()) {
return null;
}
if (data.contentEquals("null")) {
return null;
}
return data;
}
static public Response uploadCover(String typeInNode,
Long nodeId,
String file_name,
InputStream fileInputStream,
FormDataContentDisposition fileMetaData
) {
try {
// correct input string stream :
file_name = multipartCorrection(file_name);
//public NodeSmall uploadFile(final FormDataMultiPart form) {
System.out.println("Upload media file: " + fileMetaData);
System.out.println(" - id: " + nodeId);
System.out.println(" - file_name: " + file_name);
System.out.println(" - fileInputStream: " + fileInputStream);
System.out.println(" - fileMetaData: " + fileMetaData);
System.out.flush();
NodeSmall media = getWithId(typeInNode, nodeId);
if (media == null) {
return Response.notModified("Media Id does not exist or removed...").build();
}
long tmpUID = DataResource.getTmpDataId();
String sha512 = DataResource.saveTemporaryFile(fileInputStream, tmpUID);
Data data = DataResource.getWithSha512(sha512);
if (data == null) {
System.out.println("Need to add the data in the BDD ... ");
System.out.flush();
try {
data = DataResource.createNewData(tmpUID, file_name, sha512);
} catch (IOException ex) {
DataResource.removeTemporaryFile(tmpUID);
ex.printStackTrace();
return Response.notModified("can not create input media").build();
} catch (SQLException ex) {
ex.printStackTrace();
DataResource.removeTemporaryFile(tmpUID);
return Response.notModified("Error in SQL insertion ...").build();
}
} else if (data.deleted == true) {
System.out.println("Data already exist but deleted");
System.out.flush();
DataResource.undelete(data.id);
data.deleted = false;
} else {
System.out.println("Data already exist ... all good");
System.out.flush();
}
// Fist step: retrieve all the Id of each parents:...
System.out.println("Find typeNode");
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
long uniqueSQLID = -1;
// real add in the BDD:
try {
// prepare the request:
String query = "INSERT INTO cover_link_node (create_date, modify_date, node_id, data_id)" +
" VALUES (now(3), now(3), ?, ?)";
PreparedStatement ps = entry.connection.prepareStatement(query,
Statement.RETURN_GENERATED_KEYS);
int iii = 1;
ps.setLong(iii++, media.id);
ps.setLong(iii++, data.id);
// execute the request
int affectedRows = ps.executeUpdate();
if (affectedRows == 0) {
throw new SQLException("Creating data failed, no rows affected.");
}
// retreive uid inserted
try (ResultSet generatedKeys = ps.getGeneratedKeys()) {
if (generatedKeys.next()) {
uniqueSQLID = generatedKeys.getLong(1);
} else {
throw new SQLException("Creating user failed, no ID obtained (1).");
}
} catch (Exception ex) {
System.out.println("Can not get the UID key inserted ... ");
ex.printStackTrace();
throw new SQLException("Creating user failed, no ID obtained (2).");
}
} catch (SQLException ex) {
ex.printStackTrace();
entry.disconnect();
return Response.serverError().build();
}
// if we do not une the file .. remove it ... otherwise this is meamory leak...
DataResource.removeTemporaryFile(tmpUID);
System.out.println("uploaded .... compleate: " + uniqueSQLID);
return Response.ok(getWithId(typeInNode, nodeId)).build();
} catch (Exception ex) {
System.out.println("Cat ann unexpected error ... ");
ex.printStackTrace();
}
return Response.serverError().build();
}
static public Response removeCover(String typeInNode, Long nodeId, Long coverId) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "UPDATE `cover_link_node` SET `modify_date`=now(3), `deleted`=true WHERE `node_id` = ? AND `data_id` = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setLong(iii++, nodeId);
ps.setLong(iii++, coverId);
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
entry.disconnect();
return Response.serverError().build();
}
entry.disconnect();
return Response.ok(getWithId(typeInNode, nodeId)).build();
}
static public Response put(String typeInNode, Long id, String jsonRequest) {
ObjectMapper mapper = new ObjectMapper();
try {
JsonNode root = mapper.readTree(jsonRequest);
String query = "UPDATE `node` SET `modify_date`=now(3)";
if (!root.path("name").isMissingNode()) {
query += ", `name` = ? ";
}
if (!root.path("description").isMissingNode()) {
query += ", `description` = ? ";
}
if (!root.path("parentId").isMissingNode()) {
query += ", `parent_id` = ? ";
}
query += " WHERE `id` = ?";
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
if (!root.path("name").isMissingNode()) {
if (root.path("name").isNull()) {
ps.setString(iii++, "???");
} else {
ps.setString(iii++, root.path("name").asText());
}
}
if (!root.path("description").isMissingNode()) {
if (root.path("description").isNull()) {
ps.setNull(iii++, Types.VARCHAR);
} else {
ps.setString(iii++, root.path("description").asText());
}
}
if (!root.path("parentId").isMissingNode()) {
if (root.path("parentId").isNull()) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, root.path("parentId").asLong());
}
}
ps.setLong(iii++, id);
System.out.println(" request : " + ps.toString());
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
entry.disconnect();
entry = null;
return Response.notModified("SQL error").build();
}
entry.disconnect();
entry = null;
} catch (IOException e) {
e.printStackTrace();
return Response.notModified("input json error error").build();
}
return Response.ok(getWithId(typeInNode, id)).build();
}
static public Response delete(String typeInNode, Long nodeId) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "UPDATE `node` SET `modify_date`=now(3), `deleted`=true WHERE `id` = ? AND `type` = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setLong(iii++, nodeId);
ps.setString(iii++, typeInNode);
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
entry.disconnect();
return Response.serverError().build();
}
entry.disconnect();
return Response.ok().build();
}
}

View File

@ -0,0 +1,73 @@
package org.kar.karusic.api;
import org.glassfish.jersey.media.multipart.FormDataContentDisposition;
import org.glassfish.jersey.media.multipart.FormDataParam;
import org.kar.karusic.model.NodeSmall;
import javax.annotation.security.PermitAll;
import javax.annotation.security.RolesAllowed;
import javax.ws.rs.*;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import java.io.InputStream;
import java.util.List;
@Path("/season")
@Produces({MediaType.APPLICATION_JSON})
public class SeasonResource {
private static final String typeInNode = "SEASON";
@GET
@Path("{id}")
@RolesAllowed("USER")
public static NodeSmall getWithId(@PathParam("id") Long id) {
return NodeInterface.getWithId(typeInNode, id);
}
public static List<NodeSmall> getWithName(String name) {
return NodeInterface.getWithName(typeInNode, name);
}
public static NodeSmall getOrCreate(int season, Long seriesId) {
return NodeInterface.getOrCreate(typeInNode, Integer.toString(season), seriesId);
}
@GET
@RolesAllowed("USER")
public List<NodeSmall> get() {
return NodeInterface.get(typeInNode);
}
@PUT
@Path("{id}")
@RolesAllowed("ADMIN")
@Consumes(MediaType.APPLICATION_JSON)
public Response put(@PathParam("id") Long id, String jsonRequest) {
return NodeInterface.put(typeInNode, id, jsonRequest);
}
@DELETE
@Path("{id}")
@RolesAllowed("ADMIN")
public Response delete(@PathParam("id") Long id) {
return NodeInterface.delete(typeInNode, id);
}
@POST
@Path("{id}/add_cover")
@RolesAllowed("ADMIN")
@Consumes({MediaType.MULTIPART_FORM_DATA})
public Response uploadCover(@PathParam("id") Long id,
@FormDataParam("fileName") String fileName,
@FormDataParam("file") InputStream fileInputStream,
@FormDataParam("file") FormDataContentDisposition fileMetaData
) {
return NodeInterface.uploadCover(typeInNode, id, fileName, fileInputStream, fileMetaData);
}
@GET
@Path("{id}/rm_cover/{cover_id}")
@RolesAllowed("ADMIN")
public Response removeCover(@PathParam("id") Long nodeId, @PathParam("cover_id") Long coverId) {
return NodeInterface.removeCover(typeInNode, nodeId, coverId);
}
}

View File

@ -0,0 +1,77 @@
package org.kar.karusic.api;
import org.glassfish.jersey.media.multipart.FormDataContentDisposition;
import org.glassfish.jersey.media.multipart.FormDataParam;
import org.kar.karusic.model.NodeSmall;
import javax.annotation.security.PermitAll;
import javax.annotation.security.RolesAllowed;
import javax.ws.rs.*;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import java.io.InputStream;
import java.util.List;
@Path("/series")
@Produces({MediaType.APPLICATION_JSON})
public class SeriesResource {
private static final String typeInNode = "SERIES";
@GET
@Path("{id}")
@RolesAllowed("USER")
public static NodeSmall getWithId(@PathParam("id") Long id) {
return NodeInterface.getWithId(typeInNode, id);
}
public static List<NodeSmall> getWithName(String name) {
return NodeInterface.getWithName(typeInNode, name);
}
public static NodeSmall getOrCreate(String series, Long typeId) {
return NodeInterface.getOrCreate(typeInNode, series, typeId);
}
@GET
@RolesAllowed("USER")
public List<NodeSmall> get() {
return NodeInterface.get(typeInNode);
}
@PUT
@Path("{id}")
@RolesAllowed("ADMIN")
@Consumes(MediaType.APPLICATION_JSON)
public Response put(@PathParam("id") Long id, String jsonRequest) {
return NodeInterface.put(typeInNode, id, jsonRequest);
}
@DELETE
@Path("{id}")
@RolesAllowed("ADMIN")
public Response delete(@PathParam("id") Long id) {
return NodeInterface.delete(typeInNode, id);
}
@POST
@Path("{id}/add_cover")
@RolesAllowed("ADMIN")
@Consumes({MediaType.MULTIPART_FORM_DATA})
public Response uploadCover(@PathParam("id") Long id,
@FormDataParam("fileName") String fileName,
@FormDataParam("file") InputStream fileInputStream,
@FormDataParam("file") FormDataContentDisposition fileMetaData
) {
return NodeInterface.uploadCover(typeInNode, id, fileName, fileInputStream, fileMetaData);
}
@GET
@Path("{id}/rm_cover/{coverId}")
@RolesAllowed("ADMIN")
public Response removeCover(@PathParam("id") Long nodeId, @PathParam("coverId") Long coverId) {
return NodeInterface.removeCover(typeInNode, nodeId, coverId);
}
}

View File

@ -0,0 +1,69 @@
package org.kar.karusic.api;
import org.glassfish.jersey.media.multipart.FormDataContentDisposition;
import org.glassfish.jersey.media.multipart.FormDataParam;
import org.kar.karusic.model.NodeSmall;
import javax.annotation.security.PermitAll;
import javax.annotation.security.RolesAllowed;
import javax.ws.rs.*;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import java.io.InputStream;
import java.util.List;
@Path("/type")
@Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
public class TypeResource {
private static final String typeInNode = "TYPE";
@GET
@Path("{id}")
@RolesAllowed("USER")
public static NodeSmall getWithId(@PathParam("id") Long id) {
return NodeInterface.getWithId(typeInNode, id);
}
public static List<NodeSmall> getWithName(String name) {
return NodeInterface.getWithName(typeInNode, name);
}
@GET
@RolesAllowed("USER")
public List<NodeSmall> get() {
return NodeInterface.get(typeInNode);
}
@PUT
@Path("{id}")
@RolesAllowed("ADMIN")
@Consumes(MediaType.APPLICATION_JSON)
public Response put(@PathParam("id") Long id, String jsonRequest) {
return NodeInterface.put(typeInNode, id, jsonRequest);
}
@DELETE
@Path("{id}")
@RolesAllowed("ADMIN")
public Response delete(@PathParam("id") Long id) {
return NodeInterface.delete(typeInNode, id);
}
@POST
@Path("{id}/add_cover")
@RolesAllowed("ADMIN")
@Consumes({MediaType.MULTIPART_FORM_DATA})
public Response uploadCover(@PathParam("id") Long id,
@FormDataParam("file_name") String file_name,
@FormDataParam("file") InputStream fileInputStream,
@FormDataParam("file") FormDataContentDisposition fileMetaData
) {
return NodeInterface.uploadCover(typeInNode, id, file_name, fileInputStream, fileMetaData);
}
@GET
@Path("{id}/rm_cover/{cover_id}")
@RolesAllowed("ADMIN")
public Response removeCover(@PathParam("id") Long nodeId, @PathParam("cover_id") Long coverId) {
return NodeInterface.removeCover(typeInNode, nodeId, coverId);
}
}

View File

@ -0,0 +1,73 @@
package org.kar.karusic.api;
import org.glassfish.jersey.media.multipart.FormDataContentDisposition;
import org.glassfish.jersey.media.multipart.FormDataParam;
import org.kar.karusic.model.NodeSmall;
import javax.annotation.security.PermitAll;
import javax.annotation.security.RolesAllowed;
import javax.ws.rs.*;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import java.io.InputStream;
import java.util.List;
@Path("/universe")
@Produces({MediaType.APPLICATION_JSON})
public class UniverseResource {
private static final String typeInNode = "UNIVERSE";
@GET
@Path("{id}")
@RolesAllowed("USER")
public static NodeSmall getWithId(@PathParam("id") Long id) {
return NodeInterface.getWithId(typeInNode, id);
}
public static List<NodeSmall> getWithName(String name) {
return NodeInterface.getWithName(typeInNode, name);
}
public static NodeSmall getOrCreate(String universe) {
return NodeInterface.getOrCreate(typeInNode, universe, null);
}
@GET
@RolesAllowed("USER")
public List<NodeSmall> get() {
return NodeInterface.get(typeInNode);
}
@PUT
@Path("{id}")
@RolesAllowed("ADMIN")
@Consumes(MediaType.APPLICATION_JSON)
public Response put(@PathParam("id") Long id, String jsonRequest) {
return NodeInterface.put(typeInNode, id, jsonRequest);
}
@DELETE
@Path("{id}")
@RolesAllowed("ADMIN")
public Response delete(@PathParam("id") Long id) {
return NodeInterface.delete(typeInNode, id);
}
@POST
@Path("{id}/add_cover")
@RolesAllowed("ADMIN")
@Consumes({MediaType.MULTIPART_FORM_DATA})
public Response uploadCover(@PathParam("id") Long id,
@FormDataParam("fileName") String fileName,
@FormDataParam("file") InputStream fileInputStream,
@FormDataParam("file") FormDataContentDisposition fileMetaData
) {
return NodeInterface.uploadCover(typeInNode, id, fileName, fileInputStream, fileMetaData);
}
@GET
@Path("{id}/rm_cover/{cover_id}")
@RolesAllowed("ADMIN")
public Response removeCover(@PathParam("id") Long nodeId, @PathParam("cover_id") Long coverId) {
return NodeInterface.removeCover(typeInNode, nodeId, coverId);
}
}

View File

@ -0,0 +1,260 @@
package org.kar.karusic.api;
import org.kar.karusic.UserDB;
import org.kar.karusic.WebLauncher;
import org.kar.karusic.db.DBEntry;
import org.kar.karusic.filter.GenericContext;
import org.kar.karusic.model.User;
import org.kar.karusic.model.UserExtern;
import org.kar.karusic.model.UserPerso;
import javax.annotation.security.PermitAll;
import javax.annotation.security.RolesAllowed;
import javax.ws.rs.*;
import javax.ws.rs.core.Context;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.SecurityContext;
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
@Path("/users")
@Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
public class UserResource {
public UserResource() {
}
private static String randomString(int count) {
Random rand = new Random(System.nanoTime());
String s = new String();
int nbChar = count;
for (int i = 0; i < nbChar; i++) {
char c = (char) rand.nextInt();
while ((c < 'a' || c > 'z') && (c < 'A' || c > 'Z') && (c < '0' || c > '9'))
c = (char) rand.nextInt();
s = s + c;
}
return s;
}
// I do not understand why angular request option before, but this is needed..
/*
@OPTIONS
public Response getOption(){
return Response.ok()
.header("Allow", "POST")
.header("Allow", "GET")
.header("Allow", "OPTIONS")
.build();
}
*/
// curl http://localhost:9993/api/users
@GET
@RolesAllowed("ADMIN")
public List<UserExtern> getUsers() {
System.out.println("getUsers");
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
List<UserExtern> out = new ArrayList<>();
String query = "SELECT * FROM user";
try {
Statement st = entry.connection.createStatement();
ResultSet rs = st.executeQuery(query);
while (rs.next()) {
out.add(new UserExtern(new User(rs)));
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
entry = null;
return out;
}
// I do not understand why angular request option before, but this is needed..
/*
@OPTIONS
@Path("{id}")
public Response getTokenOption(@PathParam("id") long userId){
return Response.ok()
.header("Allow", "POST")
.header("Allow", "GET")
.header("Allow", "OPTIONS")
.build();
}
*/
// curl http://localhost:9993/api/users/3
@GET
@Path("{id}")
@RolesAllowed("ADMIN")
public UserExtern getUsers(@Context SecurityContext sc, @PathParam("id") long userId) {
System.out.println("getUser " + userId);
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("===================================================");
System.out.println("== USER ? " + gc.user);
System.out.println("===================================================");
return new UserExtern(UserDB.getUsers(userId));
}
/*
@OPTIONS
@Path("me")
public Response getOptionMe(){
return Response.ok()
.header("Allow", "GET")
.header("Allow", "OPTIONS")
.build();
}
*/
// curl http://localhost:9993/api/users/3
@GET
@Path("me")
@RolesAllowed("USER")
public UserPerso getMe(@Context SecurityContext sc) {
System.out.println("getMe()");
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("===================================================");
System.out.println("== USER ? " + gc.user);
System.out.println("===================================================");
return new UserPerso(gc.user);
}
// curl -d '{"id":3,"login":"HeeroYui","password":"bouloued","email":"yui.heero@gmail.com","emailValidate":0,"newEmail":null,"authorisationLevel":"ADMIN"}' -H "Content-Type: application/json" -X POST http://localhost:9993/api/users
@POST
@RolesAllowed("ADMIN")
public Response createUser(User user) {
System.out.println("getUser " + user);
/*
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT * FROM user WHERE id = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setLong(1, userId);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
User out = new User(rs);
entry.disconnect();
return out;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
entry = null;
return null;
*/
String result = "User saved ... : " + user;
return Response.status(201).entity(result).build();
}
@GET
@Path("/check_login")
@PermitAll
public Response checkLogin(@QueryParam("login") String login) {
System.out.println("checkLogin: " + login);
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT COUNT(*) FROM user WHERE login = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setString(1, login);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
int count = rs.getInt(1);
entry.disconnect();
if (count >= 1) {
return Response.ok().build();
}
return Response.status(404).build();
}
} catch (SQLException ex) {
ex.printStackTrace();
}
entry.disconnect();
return Response.status(520).build();
}
// TODO: for more security we need to hash the email when sended... or remove thios API !!!
@GET
@Path("/check_email")
@PermitAll
public Response checkEmail(@QueryParam("email") String email) {
System.out.println("checkEmail: " + email);
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT COUNT(*) FROM user WHERE email = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setString(1, email);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
int count = rs.getInt(1);
entry.disconnect();
if (count >= 1) {
return Response.ok().build();
}
return Response.status(404).build();
}
} catch (SQLException ex) {
ex.printStackTrace();
}
entry.disconnect();
return Response.status(520).build();
}
public String getSHA512(String passwordToHash) {
try {
MessageDigest md = MessageDigest.getInstance("SHA-512");
byte[] bytes = md.digest(passwordToHash.getBytes(StandardCharsets.UTF_8));
StringBuilder sb = new StringBuilder();
for (int i = 0; i < bytes.length; i++) {
sb.append(Integer.toString((bytes[i] & 0xff) + 0x100, 16).substring(1));
}
return sb.toString();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
}
return null;
}
}

View File

@ -0,0 +1,573 @@
package org.kar.karusic.api;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.glassfish.jersey.media.multipart.FormDataContentDisposition;
import org.glassfish.jersey.media.multipart.FormDataParam;
import org.kar.karusic.WebLauncher;
import org.kar.karusic.db.DBEntry;
import org.kar.karusic.model.Data;
import org.kar.karusic.model.MediaSmall;
import org.kar.karusic.model.NodeSmall;
import javax.annotation.security.PermitAll;
import javax.annotation.security.RolesAllowed;
import javax.ws.rs.*;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.Response.ResponseBuilder;
import javax.ws.rs.core.Response.Status;
import java.io.IOException;
import java.io.InputStream;
import java.sql.*;
import java.util.ArrayList;
import java.util.List;
@Path("/video")
@Produces({MediaType.APPLICATION_JSON})
public class VideoResource {
// UPDATE `node` SET `type` = "SEASON" WHERE `type` = "SAISON"
// UPDATE `node` SET `type` = "UNIVERSE" WHERE `type` = "UNIVERS"
// UPDATE `node` SET `type` = "SERIES" WHERE `type` = "SERIE"
@GET
@RolesAllowed("USER")
public List<MediaSmall> get() {
System.out.println("VIDEO get");
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
List<MediaSmall> out = new ArrayList<>();
String query = "SELECT media.id," +
" media.name," +
" media.description," +
" media.data_id," +
" media.type_id," +
" media.universe_id," +
" media.series_id," +
" media.season_id," +
" media.episode," +
" media.date," +
" media.time," +
" media.age_limit," +
" (SELECT GROUP_CONCAT(tmp.data_id SEPARATOR '-')" +
" FROM cover_link_media tmp" +
" WHERE tmp.deleted = false" +
" AND media.id = tmp.media_id" +
" GROUP BY tmp.media_id) AS covers" +
" FROM media" +
" WHERE media.deleted = false " +
" GROUP BY media.id" +
" ORDER BY media.name";
try {
Statement st = entry.connection.createStatement();
ResultSet rs = st.executeQuery(query);
while (rs.next()) {
out.add(new MediaSmall(rs));
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
entry = null;
System.out.println("retrieve " + out.size() + " VIDEO");
return out;
}
@GET
@Path("{id}")
@RolesAllowed("USER")
public MediaSmall get(@PathParam("id") Long id) {
System.out.println("VIDEO get " + id);
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "SELECT media.id," +
" media.name," +
" media.description," +
" media.data_id," +
" media.type_id," +
" media.universe_id," +
" media.series_id," +
" media.season_id," +
" media.episode," +
" media.date," +
" media.time," +
" media.age_limit," +
" (SELECT GROUP_CONCAT(tmp.data_id SEPARATOR '-')" +
" FROM cover_link_media tmp" +
" WHERE tmp.deleted = false" +
" AND media.id = tmp.media_id" +
" GROUP BY tmp.media_id) AS covers" +
" FROM media" +
" WHERE media.deleted = false " +
" AND media.id = ? " +
" GROUP BY media.id" +
" ORDER BY media.name";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setLong(iii++, id);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
MediaSmall out = new MediaSmall(rs);
entry.disconnect();
entry = null;
return out;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
entry = null;
return null;
}
@PUT
@Path("{id}")
@RolesAllowed("ADMIN")
@Consumes(MediaType.APPLICATION_JSON)
public Response put(@PathParam("id") Long id, String jsonRequest) {
ObjectMapper mapper = new ObjectMapper();
try {
JsonNode root = mapper.readTree(jsonRequest);
String query = "UPDATE `media` SET `modify_date`=now(3)";
if (!root.path("name").isMissingNode()) {
query += ", `name` = ? ";
}
if (!root.path("description").isMissingNode()) {
query += ", `description` = ? ";
}
if (!root.path("episode").isMissingNode()) {
query += ", `episode` = ? ";
}
if (!root.path("time").isMissingNode()) {
query += ", `time` = ? ";
}
if (!root.path("typeId").isMissingNode()) {
query += ", `type_id` = ? ";
}
if (!root.path("universeId").isMissingNode()) {
query += ", `universe_id` = ? ";
}
if (!root.path("seriesId").isMissingNode()) {
query += ", `series_id` = ? ";
}
if (!root.path("seasonId").isMissingNode()) {
query += ", `season_id` = ? ";
}
query += " WHERE `id` = ?";
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
if (!root.path("name").isMissingNode()) {
if (root.path("name").isNull()) {
ps.setString(iii++, "???");
} else {
ps.setString(iii++, root.path("name").asText());
}
}
if (!root.path("description").isMissingNode()) {
if (root.path("description").isNull()) {
ps.setNull(iii++, Types.VARCHAR);
} else {
ps.setString(iii++, root.path("description").asText());
}
}
if (!root.path("episode").isMissingNode()) {
if (root.path("episode").isNull()) {
ps.setNull(iii++, Types.INTEGER);
} else {
ps.setInt(iii++, root.path("episode").asInt());
}
}
if (!root.path("time").isMissingNode()) {
if (root.path("time").isNull()) {
ps.setNull(iii++, Types.INTEGER);
} else {
ps.setInt(iii++, root.path("time").asInt());
}
}
if (!root.path("typeId").isMissingNode()) {
if (root.path("typeId").isNull()) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, root.path("typeId").asLong());
}
}
if (!root.path("universe_id").isMissingNode()) {
if (root.path("universe_id").isNull()) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, root.path("universeId").asLong());
}
}
if (!root.path("seriesId").isMissingNode()) {
if (root.path("seriesId").isNull()) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, root.path("seriesId").asLong());
}
}
if (!root.path("seasonId").isMissingNode()) {
if (root.path("seasonId").isNull()) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, root.path("seasonId").asLong());
}
}
ps.setLong(iii++, id);
System.out.println(" request : " + ps.toString());
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
entry.disconnect();
entry = null;
return Response.notModified("SQL error").build();
}
entry.disconnect();
entry = null;
} catch (IOException e) {
e.printStackTrace();
return Response.notModified("input json error error").build();
}
return Response.ok(get(id)).build();
}
/*
public static void update_time(String table, Long id, Timestamp dateCreate, Timestamp dateModify) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "UPDATE " + table + " SET create_date = ?, modify_date = ? WHERE id = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
ps.setTimestamp(1, dateCreate);
ps.setTimestamp(2, dateModify);
ps.setLong(3, id);
ps.execute();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
entry.disconnect();
}
*/
private String multipartCorrection(String data) {
if (data == null) {
return null;
}
if (data.isEmpty()) {
return null;
}
if (data.contentEquals("null")) {
return null;
}
return data;
}
@POST
@Path("/upload/")
@RolesAllowed("ADMIN")
@Consumes({MediaType.MULTIPART_FORM_DATA})
public Response uploadFile(@FormDataParam("fileName") String fileName,
@FormDataParam("universe") String universe,
@FormDataParam("series") String series,
//@FormDataParam("seriesId") String seriesId, Not used ...
@FormDataParam("season") String season,
@FormDataParam("episode") String episode,
@FormDataParam("title") String title,
@FormDataParam("typeId") String typeId,
@FormDataParam("file") InputStream fileInputStream,
@FormDataParam("file") FormDataContentDisposition fileMetaData
) {
try {
// correct input string stream :
fileName = multipartCorrection(fileName);
universe = multipartCorrection(universe);
series = multipartCorrection(series);
season = multipartCorrection(season);
episode = multipartCorrection(episode);
title = multipartCorrection(title);
typeId = multipartCorrection(typeId);
//public NodeSmall uploadFile(final FormDataMultiPart form) {
System.out.println("Upload media file: " + fileMetaData);
System.out.println(" - fileName: " + fileName);
System.out.println(" - universe: " + universe);
System.out.println(" - series: " + series);
System.out.println(" - season: " + season);
System.out.println(" - episode: " + episode);
System.out.println(" - title: " + title);
System.out.println(" - type: " + typeId);
System.out.println(" - fileInputStream: " + fileInputStream);
System.out.println(" - fileMetaData: " + fileMetaData);
System.out.flush();
if (typeId == null) {
return Response.status(406).
entity("Missong Input 'type'").
type("text/plain").
build();
}
long tmpUID = DataResource.getTmpDataId();
String sha512 = DataResource.saveTemporaryFile(fileInputStream, tmpUID);
Data data = DataResource.getWithSha512(sha512);
if (data == null) {
System.out.println("Need to add the data in the BDD ... ");
System.out.flush();
try {
data = DataResource.createNewData(tmpUID, fileName, sha512);
} catch (IOException ex) {
DataResource.removeTemporaryFile(tmpUID);
ex.printStackTrace();
return Response.notModified("can not create input media").build();
} catch (SQLException ex) {
ex.printStackTrace();
DataResource.removeTemporaryFile(tmpUID);
return Response.notModified("Error in SQL insertion ...").build();
}
} else if (data.deleted == true) {
System.out.println("Data already exist but deleted");
System.out.flush();
DataResource.undelete(data.id);
data.deleted = false;
} else {
System.out.println("Data already exist ... all good");
System.out.flush();
}
// Fist step: retive all the Id of each parents:...
System.out.println("Find typeNode");
// check if id of type exist:
NodeSmall typeNode = TypeResource.getWithId(Long.parseLong(typeId));
if (typeNode == null) {
DataResource.removeTemporaryFile(tmpUID);
return Response.notModified("TypeId does not exist ...").build();
}
System.out.println(" ==> " + typeNode);
System.out.println("Find universeNode");
// get id of universe:
NodeSmall universeNode = UniverseResource.getOrCreate(universe);
System.out.println(" ==> " + universeNode);
System.out.println("Find seriesNode");
// get uid of group:
NodeSmall seriesNode = SeriesResource.getOrCreate(series, typeNode.id);
System.out.println(" ==> " + seriesNode);
System.out.println("Find seasonNode");
// get uid of season:
Integer seasonId = null;
NodeSmall seasonNode = null;
try {
seasonId = Integer.parseInt(season);
seasonNode = SeasonResource.getOrCreate(Integer.parseInt(season), seriesNode.id);
} catch (java.lang.NumberFormatException ex) {
// nothing to do ....
}
System.out.println(" ==> " + seasonNode);
System.out.println("add media");
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
long uniqueSQLID = -1;
// real add in the BDD:
try {
// prepare the request:
String query = "INSERT INTO media (create_date, modify_date, name, data_id, type_id, universe_id, series_id, season_id, episode)" +
" VALUES (now(3), now(3), ?, ?, ?, ?, ?, ?, ?)";
PreparedStatement ps = entry.connection.prepareStatement(query,
Statement.RETURN_GENERATED_KEYS);
int iii = 1;
ps.setString(iii++, title);
ps.setLong(iii++, data.id);
ps.setLong(iii++, typeNode.id);
if (universeNode == null) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, universeNode.id);
}
if (seriesNode == null) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, seriesNode.id);
}
if (seasonNode == null) {
ps.setNull(iii++, Types.BIGINT);
} else {
ps.setLong(iii++, seasonNode.id);
}
if (episode == null || episode.contentEquals("")) {
ps.setNull(iii++, Types.INTEGER);
} else {
ps.setInt(iii++, Integer.parseInt(episode));
}
// execute the request
int affectedRows = ps.executeUpdate();
if (affectedRows == 0) {
throw new SQLException("Creating data failed, no rows affected.");
}
// retreive uid inserted
try (ResultSet generatedKeys = ps.getGeneratedKeys()) {
if (generatedKeys.next()) {
uniqueSQLID = generatedKeys.getLong(1);
} else {
throw new SQLException("Creating user failed, no ID obtained (1).");
}
} catch (Exception ex) {
System.out.println("Can not get the UID key inserted ... ");
ex.printStackTrace();
throw new SQLException("Creating user failed, no ID obtained (2).");
}
} catch (SQLException ex) {
ex.printStackTrace();
}
// if we do not une the file .. remove it ... otherwise this is meamory leak...
DataResource.removeTemporaryFile(tmpUID);
System.out.println("uploaded .... compleate: " + uniqueSQLID);
MediaSmall creation = get(uniqueSQLID);
return Response.ok(creation).build();
} catch (Exception ex) {
System.out.println("Catch an unexpected error ... " + ex.getMessage());
ex.printStackTrace();
return Response.status(417).
entity("Back-end error : " + ex.getMessage()).
type("text/plain").
build();
}
}
@POST
@Path("{id}/add_cover")
@RolesAllowed("ADMIN")
@Consumes({MediaType.MULTIPART_FORM_DATA})
public Response uploadCover(@PathParam("id") Long id,
@FormDataParam("fileName") String fileName,
@FormDataParam("file") InputStream fileInputStream,
@FormDataParam("file") FormDataContentDisposition fileMetaData
) {
try {
// correct input string stream :
fileName = multipartCorrection(fileName);
//public NodeSmall uploadFile(final FormDataMultiPart form) {
System.out.println("Upload media file: " + fileMetaData);
System.out.println(" - id: " + id);
System.out.println(" - fileName: " + fileName);
System.out.println(" - fileInputStream: " + fileInputStream);
System.out.println(" - fileMetaData: " + fileMetaData);
System.out.flush();
MediaSmall media = get(id);
if (media == null) {
return Response.notModified("Media Id does not exist or removed...").build();
}
long tmpUID = DataResource.getTmpDataId();
String sha512 = DataResource.saveTemporaryFile(fileInputStream, tmpUID);
Data data = DataResource.getWithSha512(sha512);
if (data == null) {
System.out.println("Need to add the data in the BDD ... ");
System.out.flush();
try {
data = DataResource.createNewData(tmpUID, fileName, sha512);
} catch (IOException ex) {
DataResource.removeTemporaryFile(tmpUID);
ex.printStackTrace();
return Response.notModified("can not create input media").build();
} catch (SQLException ex) {
ex.printStackTrace();
DataResource.removeTemporaryFile(tmpUID);
return Response.notModified("Error in SQL insertion ...").build();
}
} else if (data.deleted == true) {
System.out.println("Data already exist but deleted");
System.out.flush();
DataResource.undelete(data.id);
data.deleted = false;
} else {
System.out.println("Data already exist ... all good");
System.out.flush();
}
// Fist step: retrieve all the Id of each parents:...
System.out.println("Find typeNode");
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
long uniqueSQLID = -1;
// real add in the BDD:
try {
// prepare the request:
String query = "INSERT INTO cover_link_media (create_date, modify_date, media_id, data_id)" +
" VALUES (now(3), now(3), ?, ?)";
PreparedStatement ps = entry.connection.prepareStatement(query,
Statement.RETURN_GENERATED_KEYS);
int iii = 1;
ps.setLong(iii++, media.id);
ps.setLong(iii++, data.id);
// execute the request
int affectedRows = ps.executeUpdate();
if (affectedRows == 0) {
throw new SQLException("Creating data failed, no rows affected.");
}
// retreive uid inserted
try (ResultSet generatedKeys = ps.getGeneratedKeys()) {
if (generatedKeys.next()) {
uniqueSQLID = generatedKeys.getLong(1);
} else {
throw new SQLException("Creating user failed, no ID obtained (1).");
}
} catch (Exception ex) {
System.out.println("Can not get the UID key inserted ... ");
ex.printStackTrace();
throw new SQLException("Creating user failed, no ID obtained (2).");
}
} catch (SQLException ex) {
ex.printStackTrace();
}
// if we do not une the file .. remove it ... otherwise this is meamory leak...
DataResource.removeTemporaryFile(tmpUID);
System.out.println("uploaded .... compleate: " + uniqueSQLID);
MediaSmall creation = get(id);
return Response.ok(creation).build();
} catch (Exception ex) {
System.out.println("Cat ann unexpected error ... ");
ex.printStackTrace();
}
return Response.serverError().build();
}
@GET
@Path("{id}/rm_cover/{cover_id}")
@RolesAllowed("ADMIN")
public Response removeCover(@PathParam("id") Long mediaId, @PathParam("cover_id") Long coverId) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "UPDATE `cover_link_media` SET `modify_date`=now(3), `deleted`=true WHERE `media_id` = ? AND `data_id` = ?";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setLong(iii++, mediaId);
ps.setLong(iii++, coverId);
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
entry.disconnect();
return Response.serverError().build();
}
entry.disconnect();
return Response.ok(get(mediaId)).build();
}
@DELETE
@Path("{id}")
@RolesAllowed("ADMIN")
public Response delete(@PathParam("id") Long id) {
DBEntry entry = new DBEntry(WebLauncher.dbConfig);
String query = "UPDATE `media` SET `modify_date`=now(3), `deleted`=true WHERE `id` = ? and `deleted` = false ";
try {
PreparedStatement ps = entry.connection.prepareStatement(query);
int iii = 1;
ps.setLong(iii++, id);
ps.executeUpdate();
} catch (SQLException throwables) {
throwables.printStackTrace();
entry.disconnect();
return Response.serverError().build();
}
entry.disconnect();
return Response.ok().build();
}
}

View File

@ -0,0 +1,60 @@
package org.kar.karusic.db;
public class DBConfig {
private final String hostname;
private final int port;
private final String login;
private final String password;
private final String dbName;
public DBConfig(String hostname, Integer port, String login, String password, String dbName) {
if (hostname == null) {
this.hostname = "localhost";
} else {
this.hostname = hostname;
}
if (port == null) {
this.port = 3306;
} else {
this.port = port;
}
this.login = login;
this.password = password;
this.dbName = dbName;
}
@Override
public String toString() {
return "DBConfig{" +
"hostname='" + hostname + '\'' +
", port=" + port +
", login='" + login + '\'' +
", password='" + password + '\'' +
", dbName='" + dbName + '\'' +
'}';
}
public String getHostname() {
return hostname;
}
public int getPort() {
return port;
}
public String getLogin() {
return login;
}
public String getPassword() {
return password;
}
public String getDbName() {
return dbName;
}
public String getUrl() {
return "jdbc:mysql://" + this.hostname + ":" + this.port + "/" + this.dbName + "?useSSL=false&serverTimezone=UTC";
}
}

View File

@ -0,0 +1,44 @@
package org.kar.karusic.db;
import org.kar.karusic.model.User;
import java.sql.*;
public class DBEntry {
public DBConfig config;
public Connection connection;
public DBEntry(DBConfig config) {
this.config = config;
connect();
}
public void connect() {
try {
connection = DriverManager.getConnection(config.getUrl(), config.getLogin(), config.getPassword());
} catch (SQLException ex) {
ex.printStackTrace();
}
}
public void disconnect() {
try {
//connection.commit();
connection.close();
} catch (SQLException ex) {
ex.printStackTrace();
}
}
public void test() throws SQLException {
String query = "SELECT * FROM user";
Statement st = connection.createStatement();
ResultSet rs = st.executeQuery(query);
System.out.println("List of user:");
if (rs.next()) {
User user = new User(rs);
System.out.println(" - " + user);
}
}
}

View File

@ -0,0 +1,199 @@
package org.kar.karusic.filter;
import java.lang.reflect.Method;
import javax.annotation.security.DenyAll;
import javax.annotation.security.PermitAll;
import javax.annotation.security.RolesAllowed;
import javax.annotation.Priority;
import javax.ws.rs.Priorities;
import javax.ws.rs.QueryParam;
import javax.ws.rs.container.ContainerRequestContext;
import javax.ws.rs.container.ContainerRequestFilter;
import javax.ws.rs.container.ResourceInfo;
import javax.ws.rs.core.Context;
import javax.ws.rs.core.HttpHeaders;
import javax.ws.rs.core.MultivaluedMap;
import javax.ws.rs.core.PathSegment;
import javax.ws.rs.core.Response;
import javax.ws.rs.ext.Provider;
import org.kar.karusic.UserDB;
import org.kar.karusic.annotation.PermitTokenInURI;
import org.kar.karusic.model.User;
import org.kar.karusic.model.UserSmall;
import org.kar.karusic.util.JWTWrapper;
import com.nimbusds.jwt.JWTClaimsSet;
import java.io.IOException;
import java.util.Arrays;
import java.util.List;
import java.util.Map.Entry;
// https://stackoverflow.com/questions/26777083/best-practice-for-rest-token-based-authentication-with-jax-rs-and-jersey
// https://stackoverflow.com/questions/26777083/best-practice-for-rest-token-based-authentication-with-jax-rs-and-jersey/45814178#45814178
// https://stackoverflow.com/questions/32817210/how-to-access-jersey-resource-secured-by-rolesallowed
//@PreMatching
@Provider
@Priority(Priorities.AUTHENTICATION)
public class AuthenticationFilter implements ContainerRequestFilter {
@Context
private ResourceInfo resourceInfo;
private static final String AUTHENTICATION_SCHEME = "Yota";
@Override
public void filter(ContainerRequestContext requestContext) throws IOException {
/*
System.out.println("-----------------------------------------------------");
System.out.println("---- Check if have authorization ----");
System.out.println("-----------------------------------------------------");
System.out.println(" for:" + requestContext.getUriInfo().getPath());
*/
Method method = resourceInfo.getResourceMethod();
// Access denied for all
if(method.isAnnotationPresent(DenyAll.class)) {
System.out.println(" ==> deny all " + requestContext.getUriInfo().getPath());
requestContext.abortWith(Response.status(Response.Status.FORBIDDEN).entity("Access blocked !!!").build());
return;
}
//Access allowed for all
if( method.isAnnotationPresent(PermitAll.class)) {
System.out.println(" ==> permit all " + requestContext.getUriInfo().getPath());
// no control ...
return;
}
// this is a security guard, all the API must define their access level:
if(!method.isAnnotationPresent(RolesAllowed.class)) {
System.out.println(" ==> missin @RolesAllowed " + requestContext.getUriInfo().getPath());
requestContext.abortWith(Response.status(Response.Status.FORBIDDEN).entity("Access ILLEGAL !!!").build());
return;
}
// Get the Authorization header from the request
String authorizationHeader = requestContext.getHeaderString(HttpHeaders.AUTHORIZATION);
//System.out.println("authorizationHeader: " + authorizationHeader);
if(authorizationHeader == null && method.isAnnotationPresent(PermitTokenInURI.class)) {
MultivaluedMap<String, String> quaryparam = requestContext.getUriInfo().getQueryParameters();
for (Entry<String, List<String>> item: quaryparam.entrySet()) {
if (item.getKey().equals(HttpHeaders.AUTHORIZATION)) {
if (!item.getValue().isEmpty()) {
authorizationHeader = item.getValue().get(0);
}
break;
}
}
}
//System.out.println("authorizationHeader: " + authorizationHeader);
/*
System.out.println(" -------------------------------");
// this get the parameters inside the pre-parsed element in the request ex: @Path("thumbnail/{id}") generate a map with "id"
MultivaluedMap<String, String> pathparam = requestContext.getUriInfo().getPathParameters();
for (Entry<String, List<String>> item: pathparam.entrySet()) {
System.out.println(" param: " + item.getKey() + " ==>" + item.getValue());
}
System.out.println(" -------------------------------");
// need to add "@QueryParam("p") String token, " in the model
//MultivaluedMap<String, String> quaryparam = requestContext.getUriInfo().getQueryParameters();
for (Entry<String, List<String>> item: quaryparam.entrySet()) {
System.out.println(" query: " + item.getKey() + " ==>" + item.getValue());
}
System.out.println(" -------------------------------");
List<PathSegment> segments = requestContext.getUriInfo().getPathSegments();
for (final PathSegment item: segments) {
System.out.println(" query: " + item.getPath() + " ==>" + item.getMatrixParameters());
}
System.out.println(" -------------------------------");
MultivaluedMap<String, String> headers = requestContext.getHeaders();
for (Entry<String, List<String>> item: headers.entrySet()) {
System.out.println(" headers: " + item.getKey() + " ==>" + item.getValue());
}
System.out.println(" -------------------------------");
*/
// Validate the Authorization header data Model "Yota userId:token"
if (!isTokenBasedAuthentication(authorizationHeader)) {
System.out.println("REJECTED unauthorized: " + requestContext.getUriInfo().getPath());
abortWithUnauthorized(requestContext);
return;
}
// check JWT token (basic:)
// Extract the token from the Authorization header (Remove "Yota ")
String token = authorizationHeader.substring(AUTHENTICATION_SCHEME.length()).trim();
System.out.println("token: " + token);
User user = null;
try {
user = validateToken(token);
} catch (Exception e) {
abortWithUnauthorized(requestContext);
}
if (user == null) {
abortWithUnauthorized(requestContext);
}
// create the security context model:
String scheme = requestContext.getUriInfo().getRequestUri().getScheme();
MySecurityContext userContext = new MySecurityContext(user, scheme);
// retrieve the allowed right:
RolesAllowed rolesAnnotation = method.getAnnotation(RolesAllowed.class);
List<String> roles = Arrays.asList(rolesAnnotation.value());
// check if the user have the right:
boolean haveRight = false;
for (String role : roles) {
if (userContext.isUserInRole(role)) {
haveRight = true;
break;
}
}
//Is user valid?
if( ! haveRight) {
System.out.println("REJECTED not enought right : " + requestContext.getUriInfo().getPath() + " require: " + roles);
requestContext.abortWith(Response.status(Response.Status.UNAUTHORIZED).entity("Not enought RIGHT !!!").build());
return;
}
requestContext.setSecurityContext(userContext);
System.out.println("Get local user : " + user);
}
private boolean isTokenBasedAuthentication(String authorizationHeader) {
// Check if the Authorization header is valid
// It must not be null and must be prefixed with "Bearer" plus a whitespace
// The authentication scheme comparison must be case-insensitive
return authorizationHeader != null && authorizationHeader.toLowerCase().startsWith(AUTHENTICATION_SCHEME.toLowerCase() + " ");
}
private void abortWithUnauthorized(ContainerRequestContext requestContext) {
// Abort the filter chain with a 401 status code response
// The WWW-Authenticate header is sent along with the response
requestContext.abortWith(
Response.status(Response.Status.UNAUTHORIZED)
.header(HttpHeaders.WWW_AUTHENTICATE,
AUTHENTICATION_SCHEME + " base64(HEADER).base64(CONTENT).base64(KEY)")
.build());
}
private User validateToken(String authorization) throws Exception {
System.out.println(" validate token : " + authorization);
JWTClaimsSet ret = JWTWrapper.validateToken(authorization, "KarAuth");
// check the token is valid !!! (signed and coherent issuer...
if (ret == null) {
System.out.println("The token is not valid: '" + authorization + "'");
return null;
}
// check userID
String userUID = ret.getSubject();
long id = Long.parseLong(userUID);
System.out.println("request user: '" + userUID + "'");
return UserDB.getUserOrCreate(id, (String)ret.getClaim("login") );
}
}

View File

@ -0,0 +1,25 @@
package org.kar.karusic.filter;
import javax.ws.rs.container.ContainerRequestContext;
import javax.ws.rs.container.ContainerResponseContext;
import javax.ws.rs.container.ContainerResponseFilter;
import javax.ws.rs.ext.Provider;
import java.io.IOException;
@Provider
public class CORSFilter implements ContainerResponseFilter {
@Override
public void filter(ContainerRequestContext request,
ContainerResponseContext response) throws IOException {
//System.err.println("filter cors ..." + request.toString());
response.getHeaders().add("Access-Control-Allow-Origin", "*");
response.getHeaders().add("Access-Control-Allow-Headers", "*");
// "Origin, content-type, Content-type, Accept, authorization, mime-type, filename");
response.getHeaders().add("Access-Control-Allow-Credentials", "true");
response.getHeaders().add("Access-Control-Allow-Methods",
"GET, POST, PUT, DELETE, OPTIONS, HEAD");
}
}

View File

@ -0,0 +1,22 @@
package org.kar.karusic.filter;
import org.kar.karusic.model.User;
import java.security.Principal;
public class GenericContext implements Principal {
public User user;
public GenericContext(User user) {
this.user = user;
}
@Override
public String getName() {
if (user == null) {
return "???";
}
return user.login;
}
}

View File

@ -0,0 +1,47 @@
package org.kar.karusic.filter;
import org.kar.karusic.model.User;
import javax.ws.rs.core.SecurityContext;
import java.security.Principal;
// https://simplapi.wordpress.com/2015/09/19/jersey-jax-rs-securitycontext-in-action/
class MySecurityContext implements SecurityContext {
private final GenericContext contextPrincipale;
private final String sheme;
public MySecurityContext(User user, String sheme) {
this.contextPrincipale = new GenericContext(user);
this.sheme = sheme;
}
@Override
public Principal getUserPrincipal() {
return contextPrincipale;
}
@Override
public boolean isUserInRole(String role) {
if (role.contentEquals("ADMIN")) {
return contextPrincipale.user.admin == true;
}
if (role.contentEquals("USER")) {
// if not an admin, this is a user...
return true; //contextPrincipale.user.admin == false;
}
return false;
}
@Override
public boolean isSecure() {
return true;
}
@Override
public String getAuthenticationScheme() {
return "Yota";
}
}

View File

@ -0,0 +1,21 @@
package org.kar.karusic.filter;
import javax.ws.rs.container.ContainerRequestContext;
import javax.ws.rs.container.ContainerRequestFilter;
import javax.ws.rs.container.PreMatching;
import javax.ws.rs.core.Response;
import javax.ws.rs.ext.Provider;
import java.io.IOException;
@Provider
@PreMatching
public class OptionFilter implements ContainerRequestFilter {
@Override
public void filter(ContainerRequestContext requestContext) throws IOException {
if (requestContext.getMethod().contentEquals("OPTIONS")) {
requestContext.abortWith(Response.status(Response.Status.NO_CONTENT).build());
}
}
}

View File

@ -0,0 +1,60 @@
package org.kar.karusic.internal;
//import io.scenarium.logger.LogLevel;
//import io.scenarium.logger.Logger;
public class Log {
// private static final String LIB_NAME = "logger";
// private static final String LIB_NAME_DRAW = Logger.getDrawableName(LIB_NAME);
// private static final boolean PRINT_CRITICAL = Logger.getNeedPrint(LIB_NAME, LogLevel.CRITICAL);
// private static final boolean PRINT_ERROR = Logger.getNeedPrint(LIB_NAME, LogLevel.ERROR);
// private static final boolean PRINT_WARNING = Logger.getNeedPrint(LIB_NAME, LogLevel.WARNING);
// private static final boolean PRINT_INFO = Logger.getNeedPrint(LIB_NAME, LogLevel.INFO);
// private static final boolean PRINT_DEBUG = Logger.getNeedPrint(LIB_NAME, LogLevel.DEBUG);
// private static final boolean PRINT_VERBOSE = Logger.getNeedPrint(LIB_NAME, LogLevel.VERBOSE);
// private static final boolean PRINT_TODO = Logger.getNeedPrint(LIB_NAME, LogLevel.TODO);
// private static final boolean PRINT_PRINT = Logger.getNeedPrint(LIB_NAME, LogLevel.PRINT);
//
// private Log() {}
//
// public static void print(String data) {
// if (PRINT_PRINT)
// Logger.print(LIB_NAME_DRAW, data);
// }
//
// public static void todo(String data) {
// if (PRINT_TODO)
// Logger.todo(LIB_NAME_DRAW, data);
// }
//
// public static void critical(String data) {
// if (PRINT_CRITICAL)
// Logger.critical(LIB_NAME_DRAW, data);
// }
//
// public static void error(String data) {
// if (PRINT_ERROR)
// Logger.error(LIB_NAME_DRAW, data);
// }
//
// public static void warning(String data) {
// if (PRINT_WARNING)
// Logger.warning(LIB_NAME_DRAW, data);
// }
//
// public static void info(String data) {
// if (PRINT_INFO)
// Logger.info(LIB_NAME_DRAW, data);
// }
//
// public static void debug(String data) {
// if (PRINT_DEBUG)
// Logger.debug(LIB_NAME_DRAW, data);
// }
//
// public static void verbose(String data) {
// if (PRINT_VERBOSE)
// Logger.verbose(LIB_NAME_DRAW, data);
// }
}

View File

@ -0,0 +1,63 @@
package org.kar.karusic.model;
/*
CREATE TABLE `node` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`deleted` BOOLEAN NOT NULL DEFAULT false,
`create_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been created',
`modify_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been update',
`type` enum("TYPE", "UNIVERS", "SERIE", "SAISON", "MEDIA") NOT NULL DEFAULT 'TYPE',
`name` TEXT COLLATE 'utf8_general_ci' NOT NULL,
`description` TEXT COLLATE 'utf8_general_ci',
`parent_id` bigint
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Date;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
@JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class Album extends Playlist {
Date publication = null;
public Album() {
}
public Album(ResultSet rs) {
super(rs);
int iii = super.getRsCount();;
try {
this.publication = rs.getDate(iii++);
if (rs.wasNull()) {
this.publication = null;
}
} catch (SQLException ex) {
ex.printStackTrace();
}
}
@Override
public int getRsCount() {
return super.getRsCount() + 1;
}
@Override
public String toString() {
return "Album [id=" + id + ", name=" + name + ", description=" + description + ", covers=" + covers
+ ", tracks=" + tracks + ", publication=" + publication + "]";
}
@Override
public String getTableSql(String tableName) {
return super.getTableSql(tableName).replaceAll("<<<TABLE_ADDITION>>>", """
`publication` timestamp(3) NULL COMMENT 'death date of the artist',
<<<TABLE_ADDITION>>>
""");
}
@Override
public String getTableSql() {
return getTableSql("album").replaceAll("<<<.*>>>", "");
}
}

View File

@ -0,0 +1,79 @@
package org.kar.karusic.model;
/*
CREATE TABLE `node` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`deleted` BOOLEAN NOT NULL DEFAULT false,
`create_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been created',
`modify_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been update',
`type` enum("TYPE", "UNIVERS", "SERIE", "SAISON", "MEDIA") NOT NULL DEFAULT 'TYPE',
`name` TEXT COLLATE 'utf8_general_ci' NOT NULL,
`description` TEXT COLLATE 'utf8_general_ci',
`parent_id` bigint
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Date;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
@JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class Artist extends NodeSmall {
String firstName = null;
String surname = null;
Date birth = null;
Date death = null;
public Artist() {
}
public Artist(ResultSet rs) {
super(rs);
int iii = super.getRsCount();;
try {
this.firstName = rs.getString(iii++);
if (rs.wasNull()) {
this.firstName = null;
}
this.surname = rs.getString(iii++);
if (rs.wasNull()) {
this.surname = null;
}
this.birth = rs.getDate(iii++);
if (rs.wasNull()) {
this.birth = null;
}
this.death = rs.getDate(iii++);
if (rs.wasNull()) {
this.death = null;
}
} catch (SQLException ex) {
ex.printStackTrace();
}
}
@Override
public int getRsCount() {
return super.getRsCount() + 4;
}
@Override
public String toString() {
return "Artist [id=" + id + ", name=" + name + ", description=" + description + ", covers=" + covers +
", firstName=" + firstName + ", surname=" + surname + ", birth=" + birth + ", death=" + death + "]";
}
@Override
public String getTableSql(String tableName) {
return super.getTableSql(tableName).replaceAll("<<<TABLE_ADDITION>>>", """
`firstName` varchar(256) NOT NULL,
`surname` varchar(256) NOT NULL,
`birth` timestamp(3) NULL COMMENT 'birth date of the artist',
`death` timestamp(3) NULL COMMENT 'death date of the artist',
<<<TABLE_ADDITION>>>
""");
}
@Override
public String getTableSql() {
return getTableSql("artist").replaceAll("<<<.*>>>", "");
}
}

View File

@ -0,0 +1,32 @@
package org.kar.karusic.model;
import java.sql.ResultSet;
import java.sql.SQLException;
public class Data {
public Long id;
public boolean deleted;
public String sha512;
public String mimeType;
public Long size;
public Data() {
}
public Data(ResultSet rs) {
int iii = 1;
try {
this.id = rs.getLong(iii++);
this.deleted = rs.getBoolean(iii++);
this.sha512 = rs.getString(iii++);
this.mimeType = rs.getString(iii++);
this.size = rs.getLong(iii++);
if (rs.wasNull()) {
this.size = null;
}
} catch (SQLException ex) {
ex.printStackTrace();
}
}
}

View File

@ -0,0 +1,8 @@
package org.kar.karusic.model;
public class DataGetToken {
public String login;
public String method;
public String time;
public String password;
}

View File

@ -0,0 +1,55 @@
package org.kar.karusic.model;
/*
CREATE TABLE `data` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`deleted` BOOLEAN NOT NULL DEFAULT false,
`create_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been created',
`modify_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been update',
`sha512` varchar(129) COLLATE 'utf8_general_ci' NOT NULL,
`mime_type` varchar(128) COLLATE 'utf8_general_ci' NOT NULL,
`size` bigint,
`original_name` TEXT
) AUTO_INCREMENT=64;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
public class DataSmall {
public Long id;
public String sha512;
public String mimeType;
public Long size;
public DataSmall() {
}
public DataSmall(ResultSet rs) {
int iii = 1;
try {
this.id = rs.getLong(iii++);
this.sha512 = rs.getString(iii++);
this.mimeType = rs.getString(iii++);
this.size = rs.getLong(iii++);
} catch (SQLException ex) {
ex.printStackTrace();
}
}
public String getTableSql() {
return """
DROP TABLE IF EXISTS `data`;
CREATE TABLE `data` (
`id` bigint NOT NULL AUTO_INCREMENT COMMENT 'table ID',
`deleted` tinyint(1) NOT NULL DEFAULT '0',
`create_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) COMMENT 'Time the element has been created',
`modify_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) COMMENT 'Time the element has been update',
`sha512` varchar(129) CHARACTER SET utf8mb3 COLLATE utf8_general_ci NOT NULL,
`mime_type` varchar(128) CHARACTER SET utf8mb3 COLLATE utf8_general_ci NOT NULL,
`size` bigint DEFAULT NULL,
`original_name` text,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
""";
}
}

View File

@ -0,0 +1,42 @@
package org.kar.karusic.model;
/*
CREATE TABLE `node` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`deleted` BOOLEAN NOT NULL DEFAULT false,
`create_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been created',
`modify_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been update',
`type` enum("TYPE", "UNIVERS", "SERIE", "SAISON", "MEDIA") NOT NULL DEFAULT 'TYPE',
`name` TEXT COLLATE 'utf8_general_ci' NOT NULL,
`description` TEXT COLLATE 'utf8_general_ci',
`parent_id` bigint
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
@JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class Gender extends NodeSmall {
public Gender() {
}
public Gender(ResultSet rs) {
super(rs);
// nothing to do...
}
@Override
public int getRsCount() {
return super.getRsCount() + 0;
}
@Override
public String toString() {
return "Gender [id=" + id + ", name=" + name + ", description=" + description + ", covers=" + covers + "]";
}
@Override
public String getTableSql() {
return getTableSql("gender").replaceAll("<<<.*>>>", "");
}
}

View File

@ -0,0 +1,80 @@
package org.kar.karusic.model;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
public abstract class GenericTable {
protected String tableName = "plopppppp";
public Long id = null;
GenericTable(String tableName) {
this.tableName = tableName;
}
protected GenericTable(String tableName, ResultSet rs) {
this.tableName = tableName;
int iii = 1;
try {
this.id = rs.getLong(iii++);
} catch (SQLException ex) {
ex.printStackTrace();
}
}
protected List<Long> getListOfIds(ResultSet rs, int iii) throws SQLException {
String trackString = rs.getString(iii);
if (rs.wasNull()) {
return null;
}
List<Long> out = new ArrayList<>();
String[] elements = trackString.split("-");
for (String elem : elements) {
Long tmp = Long.parseLong(elem);
out.add(tmp);
}
return out;
}
public String toStringSmall() {
return "id=" + this.id;
}
public int getRsCount() {
return 1 + 1;
}
public String getTableLinkSql(String from, String to) {
return """
DROP TABLE IF EXISTS `<<<FROM>>>_link_<<<TO>>>`;
CREATE TABLE `<<<FROM>>>_link_<<<TO>>>` (
`id` bigint NOT NULL AUTO_INCREMENT COMMENT 'table ID',
`deleted` tinyint(1) NOT NULL DEFAULT '0',
`create_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`modify_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`<<<FROM>>>_id` bigint NOT NULL,
`<<<TO>>>_id` bigint NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
<<<TABLE_OTHER>>>
""".replaceAll("<<<FROM>>>", from).replaceAll("<<<TO>>>", to);
}
public String getTableSqlModel() {
return """
DROP TABLE IF EXISTS `<<<TABLE_NAME>>>`;
CREATE TABLE `<<<TABLE_NAME>>>` (
`id` bigint NOT NULL AUTO_INCREMENT COMMENT 'table ID',
`deleted` tinyint(1) NOT NULL DEFAULT '0',
`create_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) COMMENT 'Time the element has been created',
`modify_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) COMMENT 'Time the element has been update',
<<<TABLE_ADDITION>>>
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
<<<TABLE_OTHER>>>
""".replace("<<<TABLE_OTHER>>>", getTableLinkSql("<<<TABLE_NAME>>>", "data"));
}
public final String getTableSql() {
return getTableSqlModel().replace("<<<TABLE_NAME>>>", tableName).replaceAll("<<<.*>>>", "");
}
}

View File

@ -0,0 +1,104 @@
package org.kar.karusic.model;
/*
CREATE TABLE `node` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`deleted` BOOLEAN NOT NULL DEFAULT false,
`create_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been created',
`modify_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been update',
`type` enum("TYPE", "UNIVERSE", "SERIES", "SEASON") NOT NULL DEFAULT 'TYPE',
`name` TEXT COLLATE 'utf8_general_ci' NOT NULL,
`description` TEXT COLLATE 'utf8_general_ci',
`parent_id` bigint
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
@JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class MediaSmall {
public class MediaStreamProperty {
public Long id;
public Long timeSecond;
public Long width;
public Long height;
public Map<String, Long> videos = new HashMap<>();
public Map<String, Long> audios = new HashMap<>();
public Map<String, Long> subtitles = new HashMap<>();
}
public Long id;
public String name;
public String description;
public Long dataId;
public Long typeId;
public Long universeId;
public Long seriesId;
public Long seasonId;
public Integer episode;
public Integer date;
public Integer time;
public String ageLimit;
public List<Long> covers = null;
public MediaStreamProperty media;
public MediaSmall(ResultSet rs) {
int iii = 1;
try {
this.id = rs.getLong(iii++);
this.name = rs.getString(iii++);
this.description = rs.getString(iii++);
this.dataId = rs.getLong(iii++);
if (rs.wasNull()) {
this.dataId = null;
}
this.typeId = rs.getLong(iii++);
if (rs.wasNull()) {
this.typeId = null;
}
this.universeId = rs.getLong(iii++);
if (rs.wasNull()) {
this.universeId = null;
}
this.seriesId = rs.getLong(iii++);
if (rs.wasNull()) {
this.seriesId = null;
}
this.seasonId = rs.getLong(iii++);
if (rs.wasNull()) {
this.seasonId = null;
}
this.episode = rs.getInt(iii++);
if (rs.wasNull()) {
this.episode = null;
}
this.date = rs.getInt(iii++);
if (rs.wasNull()) {
this.date = null;
}
this.time = rs.getInt(iii++);
if (rs.wasNull()) {
this.time = null;
}
this.ageLimit = rs.getString(iii++);
String coversString = rs.getString(iii++);
if (!rs.wasNull()) {
covers = new ArrayList<>();
String[] elements = coversString.split("-");
for (String elem : elements) {
Long tmp = Long.parseLong(elem);
covers.add(tmp);
}
}
} catch (SQLException ex) {
ex.printStackTrace();
}
}
}

View File

@ -0,0 +1,63 @@
package org.kar.karusic.model;
/*
CREATE TABLE `node` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`deleted` BOOLEAN NOT NULL DEFAULT false,
`create_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been created',
`modify_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been update',
`type` enum("TYPE", "UNIVERS", "SERIE", "SAISON", "MEDIA") NOT NULL DEFAULT 'TYPE',
`name` TEXT COLLATE 'utf8_general_ci' NOT NULL,
`description` TEXT COLLATE 'utf8_general_ci',
`parent_id` bigint
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
@JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class NodeSmall extends GenericTable {
public String name;
public String description;
public List<Long> covers = null;
protected NodeSmall(String tableName) {
super(tableName);
}
protected NodeSmall(String tableName, ResultSet rs) {
super(tableName, rs);
int iii = super.getRsCount();
try {
this.name = rs.getString(iii++);
this.description = rs.getString(iii++);
this.covers = getListOfIds(rs, iii++);
} catch (SQLException ex) {
ex.printStackTrace();
}
}
@Override
public String toStringSmall() {
return super.toStringSmall() +
", name='" + name + '\'' +
", description='" + description + '\'' +
", covers=" + covers +
'}';
}
@Override
public int getRsCount() {
return super.getRsCount() + 3;
}
@Override
public String getTableSql(String tableName) {
return super.getTableSql(tableName).replaceAll("<<<TABLE_ADDITION>>>", """
`name` text CHARACTER SET utf8mb3 COLLATE utf8_general_ci NOT NULL,
`description` text CHARACTER SET utf8mb3 COLLATE utf8_general_ci,
<<<TABLE_ADDITION>>>
""").replaceAll("<<<TABLE_OTHER>>>", getTableLinkSql(tableName, "data"));
}
}

View File

@ -0,0 +1,78 @@
package org.kar.karusic.model;
/*
CREATE TABLE `node` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`deleted` BOOLEAN NOT NULL DEFAULT false,
`create_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been created',
`modify_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been update',
`type` enum("TYPE", "UNIVERS", "SERIE", "SAISON", "MEDIA") NOT NULL DEFAULT 'TYPE',
`name` TEXT COLLATE 'utf8_general_ci' NOT NULL,
`description` TEXT COLLATE 'utf8_general_ci',
`parent_id` bigint
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
@JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class Playlist extends NodeSmall {
List<Long> tracks = null;
public Playlist() {
}
public Playlist(ResultSet rs) {
super(rs);
int iii = super.getRsCount();;
try {
String trackString = rs.getString(iii++);
if (!rs.wasNull()) {
this.tracks = new ArrayList<>();
String[] elements = trackString.split("-");
for (String elem : elements) {
Long tmp = Long.parseLong(elem);
this.tracks.add(tmp);
}
}
} catch (SQLException ex) {
ex.printStackTrace();
}
}
@Override
public int getRsCount() {
return super.getRsCount() + 1;
}
@Override
public String toString() {
return "Artist [id=" + id + ", name=" + name + ", description=" + description + ", covers=" + covers +
", tracksId=" + tracks + "]";
}
@Override
public String getTableSql(String tableName) {
return super.getTableSql(tableName).replaceAll("<<<TABLE_OTHER>>>", """
DROP TABLE IF EXISTS `<<<TABLE_NAME>>>_link_track`;
CREATE TABLE `<<<TABLE_NAME>>>_link_track` (
`id` bigint NOT NULL AUTO_INCREMENT COMMENT 'table ID',
`deleted` tinyint(1) NOT NULL DEFAULT '0',
`create_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`modify_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`<<<TABLE_NAME>>>_id` bigint DEFAULT NULL,
`track_id` bigint NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
<<<TABLE_OTHER>>>
""").replaceAll("<<<TABLE_NAME>>>", tableName);
}
@Override
public String getTableSql() {
return getTableSql("playlist").replaceAll("<<<.*>>>", "");
}
}

View File

@ -0,0 +1,10 @@
package org.kar.karusic.model;
public enum State {
// User has remove his account
REMOVED,
// User has been blocked his account
BLOCKED,
// generic user
USER
}

View File

@ -0,0 +1,57 @@
package org.kar.karusic.model;
import java.sql.ResultSet;
import java.sql.SQLException;
/*
CREATE TABLE `token` (
`id` bigint NOT NULL COMMENT 'Unique ID of the TOKEN' AUTO_INCREMENT PRIMARY KEY,
`userId` bigint NOT NULL COMMENT 'Unique ID of the user',
`token` varchar(128) COLLATE 'latin1_bin' NOT NULL COMMENT 'Token (can be not unique)',
`createTime` datetime NOT NULL COMMENT 'Time the token has been created',
`endValidityTime` datetime NOT NULL COMMENT 'Time of the token end validity'
) AUTO_INCREMENT=10;
*/
public class Token {
public Long id;
public Long userId;
public String token;
public String createTime;
public String endValidityTime;
public Token() {
}
public Token(long id, long userId, String token, String createTime, String endValidityTime) {
this.id = id;
this.userId = userId;
this.token = token;
this.createTime = createTime;
this.endValidityTime = endValidityTime;
}
public Token(ResultSet rs) {
int iii = 1;
try {
this.id = rs.getLong(iii++);
this.userId = rs.getLong(iii++);
this.token = rs.getString(iii++);
this.createTime = rs.getString(iii++);
this.endValidityTime = rs.getString(iii++);
} catch (SQLException ex) {
ex.printStackTrace();
}
}
@Override
public String toString() {
return "Token{" +
"id=" + id +
", userId=" + userId +
", token='" + token + '\'' +
", createTime=" + createTime +
", endValidityTime=" + endValidityTime +
'}';
}
}

View File

@ -0,0 +1,82 @@
package org.kar.karusic.model;
/*
CREATE TABLE `node` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`deleted` BOOLEAN NOT NULL DEFAULT false,
`create_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been created',
`modify_date` datetime NOT NULL DEFAULT now() COMMENT 'Time the element has been update',
`type` enum("TYPE", "UNIVERS", "SERIE", "SAISON", "MEDIA") NOT NULL DEFAULT 'TYPE',
`name` TEXT COLLATE 'utf8_general_ci' NOT NULL,
`description` TEXT COLLATE 'utf8_general_ci',
`parent_id` bigint
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
@JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class Track extends NodeSmall {
Long genderId = null;
Long dataId = null;
List<Long> artistId = null;
public Track() {
}
public Track(ResultSet rs) {
super(rs);
int iii = super.getRsCount();;
try {
this.genderId = rs.getLong(iii++);
if (rs.wasNull()) {
this.genderId = null;
}
this.dataId = rs.getLong(iii++);
if (rs.wasNull()) {
this.dataId = null;
}
this.artistId = getListOfIds(rs, iii++);
} catch (SQLException ex) {
ex.printStackTrace();
}
}
@Override
public int getRsCount() {
return super.getRsCount() + 4;
}
@Override
public String toString() {
return "Tracks [id=" + id + ", name=" + name + ", description=" + description + ", covers=" + covers +
", genderId=" + genderId + ", dataId=" + dataId + ", artistId=" + artistId + "]";
}
@Override
public String getTableSql(String tableName) {
return super.getTableSql(tableName).replaceAll("<<<TABLE_ADDITION>>>", """
`genderId` bigint NULL,
`dataId` bigint NULL,
<<<TABLE_ADDITION>>>
""").replaceAll("<<<TABLE_OTHER>>>", """
DROP TABLE IF EXISTS `<<<TABLE_NAME>>>_link_artist`;
CREATE TABLE `<<<TABLE_NAME>>>_link_artist` (
`id` bigint NOT NULL AUTO_INCREMENT COMMENT 'table ID',
`deleted` tinyint(1) NOT NULL DEFAULT '0',
`create_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`modify_date` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
`<<<TABLE_NAME>>>_id` bigint DEFAULT NULL,
`artist_id` bigint NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
<<<TABLE_OTHER>>>
""").replaceAll("<<<TABLE_NAME>>>", tableName);
}
@Override
public String getTableSql() {
return getTableSql("track").replaceAll("<<<.*>>>", "");
}
}

View File

@ -0,0 +1,81 @@
package org.kar.karusic.model;
/*
CREATE TABLE `user` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`login` varchar(128) COLLATE 'utf8_general_ci' NOT NULL COMMENT 'login of the user',
`email` varchar(512) COLLATE 'utf8_general_ci' NOT NULL COMMENT 'email of the user',
`lastConnection` datetime NOT NULL COMMENT 'last connection time',
`admin` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE',
`blocked` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE',
`removed` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE',
`avatar` bigint DEFAULT NULL,
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
public class User {
public Long id;
public String login;
public Timestamp lastConnection;
public boolean admin;
public boolean blocked;
public boolean removed;
public User() {
}
public User(Long id, String login, Timestamp lastConnection, String email, boolean admin, boolean blocked, boolean removed, Long avatar) {
this.id = id;
this.login = login;
this.lastConnection = lastConnection;
this.admin = admin;
this.blocked = blocked;
this.removed = removed;
}
public User(ResultSet rs) {
int iii = 1;
try {
this.id = rs.getLong(iii++);
this.lastConnection = rs.getTimestamp(iii++);
this.login = rs.getString(iii++);
this.admin = "TRUE".equals(rs.getString(iii++));
this.blocked = "TRUE".equals(rs.getString(iii++));
this.removed = "TRUE".equals(rs.getString(iii++));
} catch (SQLException ex) {
ex.printStackTrace();
}
}
@Override
public String toString() {
return "User{" +
"id=" + id +
", login='" + login + '\'' +
", lastConnection='" + lastConnection + '\'' +
", admin=" + admin +
", blocked=" + blocked +
", removed=" + removed +
'}';
}
public String getTableSql() {
return """
DROP TABLE IF EXISTS `user`;
CREATE TABLE `user` (
`id` bigint NOT NULL AUTO_INCREMENT COMMENT 'table ID',
`lastConnection` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) COMMENT 'last connection time',
`login` varchar(128) CHARACTER SET utf8mb3 COLLATE utf8_general_ci NOT NULL COMMENT 'login of the user',
`admin` enum('TRUE','FALSE') NOT NULL DEFAULT 'FALSE',
`blocked` enum('TRUE','FALSE') NOT NULL DEFAULT 'FALSE',
`removed` enum('TRUE','FALSE') NOT NULL DEFAULT 'FALSE',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
""";
}
}

View File

@ -0,0 +1,36 @@
package org.kar.karusic.model;
/*
CREATE TABLE `user` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`login` varchar(128) COLLATE 'utf8_general_ci' NOT NULL COMMENT 'login of the user',
`email` varchar(512) COLLATE 'utf8_general_ci' NOT NULL COMMENT 'email of the user',
`lastConnection` datetime NOT NULL COMMENT 'last connection time',
`admin` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE',
`blocked` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE',
`removed` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE'
) AUTO_INCREMENT=10;
*/
public class UserExtern {
public Long id;
public String login;
public boolean admin;
public UserExtern(User other) {
this.id = other.id;
this.login = other.login;
this.admin = other.admin;
}
@Override
public String toString() {
return "User{" +
"id=" + id +
", login='" + login + '\'' +
", admin=" + admin +
'}';
}
}

View File

@ -0,0 +1,42 @@
package org.kar.karusic.model;
/*
CREATE TABLE `user` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`login` varchar(128) COLLATE 'utf8_general_ci' NOT NULL COMMENT 'login of the user',
`email` varchar(512) COLLATE 'utf8_general_ci' NOT NULL COMMENT 'email of the user',
`lastConnection` datetime NOT NULL COMMENT 'last connection time',
`admin` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE',
`blocked` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE',
`removed` enum("TRUE", "FALSE") NOT NULL DEFAULT 'FALSE'
) AUTO_INCREMENT=10;
*/
public class UserPerso {
public Long id;
public String login;
public boolean admin;
public boolean blocked;
public boolean removed;
public UserPerso(User other) {
this.id = other.id;
this.login = other.login;
this.admin = other.admin;
this.blocked = other.blocked;
this.removed = other.removed;
}
@Override
public String toString() {
return "User{" +
"id=" + id +
", login='" + login + '\'' +
", admin=" + admin +
", blocked=" + blocked +
", removed=" + removed +
'}';
}
}

View File

@ -0,0 +1,73 @@
package org.kar.karusic.model;
/*
CREATE TABLE `user` (
`id` bigint NOT NULL COMMENT 'table ID' AUTO_INCREMENT PRIMARY KEY,
`login` varchar(128) COLLATE 'utf8_general_ci' NOT NULL COMMENT 'login of the user',
`password` varchar(128) COLLATE 'latin1_bin' NOT NULL COMMENT 'password of the user hashed (sha512)',
`email` varchar(512) COLLATE 'utf8_general_ci' NOT NULL COMMENT 'email of the user',
`emailValidate` bigint COMMENT 'date of the email validation',
`newEmail` varchar(512) COLLATE 'utf8_general_ci' COMMENT 'email of the user if he want to change',
`authorisationLevel` enum("REMOVED", "USER", "ADMIN") NOT NULL COMMENT 'user level of authorization'
) AUTO_INCREMENT=10;
*/
import java.sql.ResultSet;
import java.sql.SQLException;
public class UserSmall {
public long id;
public String login;
public String email;
public State authorisationLevel;
public UserSmall() {
}
public UserSmall(long id, String login, String email, State authorisationLevel) {
this.id = id;
this.login = login;
this.email = email;
this.authorisationLevel = authorisationLevel;
}
public UserSmall(ResultSet rs) {
int iii = 1;
try {
this.id = rs.getLong(iii++);
this.login = rs.getString(iii++);
this.email = rs.getString(iii++);
this.authorisationLevel = State.valueOf(rs.getString(iii++));
} catch (SQLException ex) {
ex.printStackTrace();
}
}
/*
public void serialize(ResultSet rs) {
int iii = 1;
try {
this.id = rs.getLong(iii++);
this.login = rs.getString(iii++);
this.password = rs.getString(iii++);
this.email = rs.getString(iii++);
this.emailValidate = rs.getLong(iii++);
this.newEmail = rs.getString(iii++);
this.authorisationLevel = State.valueOf(rs.getString(iii++));
} catch (SQLException ex) {
ex.printStackTrace();
}
}
*/
@Override
public String toString() {
return "UserSmall{" +
"id='" + id + '\'' +
", login='" + login + '\'' +
", email='" + email + '\'' +
", authorisationLevel=" + authorisationLevel +
'}';
}
}

View File

@ -0,0 +1,85 @@
package org.kar.karusic.util;
public class ConfigVariable {
public static String getTmpDataFolder() {
String out = System.getenv("org.kar.karusic.dataTmpFolder");
if (out == null) {
return "/application/data/tmp";
}
return out;
}
public static String getMediaDataFolder() {
String out = System.getenv("org.kar.karusic.dataFolder");
if (out == null) {
return "/application/data/media";
}
return out;
}
public static String getFrontFolder() {
String out = System.getenv("ORG_KARIDEO_FRONT_FOLDER");
if (out == null) {
return "/application/karusic";
}
return out;
}
public static String getDBHost() {
String out = System.getenv("ORG_KARIDEO_DB_HOST");
if (out == null) {
return "localhost";
}
return out;
}
public static String getDBPort() {
String out = System.getenv("ORG_KARIDEO_DB_PORT");
if (out == null) {
return "17036";
}
return out;
}
public static String getDBLogin() {
String out = System.getenv("ORG_KARIDEO_DB_LOGIN");
if (out == null) {
return "root";
}
return out;
}
public static String getDBPassword() {
String out = System.getenv("MYSQL_ROOT_PASSWORD");
if (out == null) {
return "ZERTYSDGFVHSDFGHJYZSDFGSQxfgsqdfgsqdrf4564654";
}
return out;
}
public static String getDBName() {
String out = System.getenv("MYSQL_DATABASE");
if (out == null) {
return "karusic";
}
return out;
}
public static String getlocalAddress() {
String out = System.getenv("ORG_KARIDEO_ADDRESS");
if (out == null) {
return "http://0.0.0.0:18080/karusic/api/";
}
return out;
}
public static String getSSOAddress() {
String out = System.getenv("SSO_ADDRESS");
if (out == null) {
return "http://192.168.1.156/karauth/api/";
}
return out;
}
}

View File

@ -0,0 +1,175 @@
package org.kar.karusic.util;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.text.ParseException;
import java.util.Date;
import java.util.UUID;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.nimbusds.jose.JOSEException;
import com.nimbusds.jose.JOSEObjectType;
import com.nimbusds.jose.JWSAlgorithm;
import com.nimbusds.jose.JWSHeader;
import com.nimbusds.jose.JWSSigner;
import com.nimbusds.jose.JWSVerifier;
import com.nimbusds.jose.crypto.RSASSASigner;
import com.nimbusds.jose.crypto.RSASSAVerifier;
import com.nimbusds.jose.jwk.RSAKey;
import com.nimbusds.jose.jwk.gen.RSAKeyGenerator;
import com.nimbusds.jwt.JWTClaimsSet;
import com.nimbusds.jwt.SignedJWT;
public class JWTWrapper {
private static RSAKey rsaJWK = null;;
private static RSAKey rsaPublicJWK = null;
public static class PublicKey {
public String key;
public PublicKey(String key) {
this.key = key;
}
public PublicKey() {
}
}
public static void initLocalTokenRemote(String ssoUri, String application) throws IOException, ParseException {
// check Token:
URL obj = new URL(ssoUri + "public_key");
System.out.println("Request token from:" + obj);
HttpURLConnection con = (HttpURLConnection) obj.openConnection();
con.setRequestMethod("GET");
con.setRequestProperty("User-Agent", application);
con.setRequestProperty("Cache-Control", "no-cache");
con.setRequestProperty("Content-Type", "application/json");
con.setRequestProperty("Accept", "application/json");
int responseCode = con.getResponseCode();
System.out.println("GET Response Code :: " + responseCode);
if (responseCode == HttpURLConnection.HTTP_OK) { // success
BufferedReader in = new BufferedReader(new InputStreamReader(con.getInputStream()));
String inputLine;
StringBuffer response = new StringBuffer();
while ((inputLine = in.readLine()) != null) {
response.append(inputLine);
}
in.close();
// print result
System.out.println(response.toString());
ObjectMapper mapper = new ObjectMapper();
;
PublicKey values = mapper.readValue(response.toString(), PublicKey.class);
rsaPublicJWK = RSAKey.parse(values.key);
}
System.out.println("GET JWT validator token not worked");
}
public static void initLocalToken() throws Exception{
// RSA signatures require a public and private RSA key pair, the public key
// must be made known to the JWS recipient in order to verify the signatures
try {
String generatedStringForKey = UUID.randomUUID().toString();
rsaJWK = new RSAKeyGenerator(2048).keyID(generatedStringForKey).generate();
rsaPublicJWK = rsaJWK.toPublicJWK();
//System.out.println("RSA key (all): " + rsaJWK.toJSONString());
//System.out.println("RSA key (pub): " + rsaPublicJWK.toJSONString());
} catch (JOSEException e) {
// TODO Auto-generated catch block
e.printStackTrace();
System.out.println("Can not generate teh public abnd private keys ...");
rsaJWK = null;
rsaPublicJWK = null;
}
}
public static void initValidateToken(String publicKey) {
try {
rsaPublicJWK = RSAKey.parse(publicKey);
} catch (ParseException e) {
e.printStackTrace();
System.out.println("Can not retrieve public Key !!!!!!!! RSAKey='" + publicKey + "'");
}
}
public static String getPublicKey() {
if (rsaPublicJWK == null) {
return null;
}
return rsaPublicJWK.toJSONString();
}
/**
* Create a token with the provided elements
* @param userID UniqueId of the USER (global unique ID)
* @param userLogin Login of the user (never change)
* @param isuer The one who provide the Token
* @param timeOutInMunites Expiration of the token.
* @return the encoded token
*/
public static String generateJWToken(long userID, String userLogin, String isuer, int timeOutInMunites) {
if (rsaJWK == null) {
System.out.println("JWT private key is not present !!!");
return null;
}
try {
// Create RSA-signer with the private key
JWSSigner signer = new RSASSASigner(rsaJWK);
// Prepare JWT with claims set
JWTClaimsSet claimsSet = new JWTClaimsSet.Builder()
.subject(Long.toString(userID))
.claim("login", userLogin)
.issuer(isuer)
.issueTime(new Date())
.expirationTime(new Date(new Date().getTime() + 60 * timeOutInMunites * 1000 /* millisecond */))
.build();
SignedJWT signedJWT = new SignedJWT(new JWSHeader.Builder(JWSAlgorithm.RS256).type(JOSEObjectType.JWT)/*.keyID(rsaJWK.getKeyID())*/.build(), claimsSet);
// Compute the RSA signature
signedJWT.sign(signer);
// serialize the output...
return signedJWT.serialize();
} catch (JOSEException ex) {
ex.printStackTrace();
}
return null;
}
public static JWTClaimsSet validateToken(String signedToken, String isuer) {
if (rsaPublicJWK == null) {
System.out.println("JWT public key is not present !!!");
return null;
}
try {
// On the consumer side, parse the JWS and verify its RSA signature
SignedJWT signedJWT = SignedJWT.parse(signedToken);
JWSVerifier verifier = new RSASSAVerifier(rsaPublicJWK);
if (!signedJWT.verify(verifier)) {
System.out.println("JWT token is NOT verified ");
return null;
}
if (!new Date().before(signedJWT.getJWTClaimsSet().getExpirationTime())) {
System.out.println("JWT token is expired now = " + new Date() + " with=" + signedJWT.getJWTClaimsSet().getExpirationTime() );
return null;
}
if (!isuer.equals(signedJWT.getJWTClaimsSet().getIssuer())) {
System.out.println("JWT issuer is wong: '" + isuer + "' != '" + signedJWT.getJWTClaimsSet().getIssuer() + "'" );
return null;
}
// the element must be validated outside ...
//System.out.println("JWT token is verified 'alice' =?= '" + signedJWT.getJWTClaimsSet().getSubject() + "'");
//System.out.println("JWT token isuer 'https://c2id.com' =?= '" + signedJWT.getJWTClaimsSet().getIssuer() + "'");
return signedJWT.getJWTClaimsSet();
} catch (JOSEException ex) {
ex.printStackTrace();
} catch (ParseException e) {
e.printStackTrace();
}
return null;
}
}

View File

@ -0,0 +1,10 @@
package org.kar.karusic.util;
public class PublicKey {
public String key;
public PublicKey(String key) {
this.key = key;
}
}

25
bdd/docker-compose.yaml Normal file
View File

@ -0,0 +1,25 @@
# Use root/example as user/password credentials
version: '3.1'
services:
db_service:
image: mysql:latest
container_name: mysql_db
restart: always
command: --default-authentication-plugin=mysql_native_password
env_file:
- ./config.env
#environment:
# MYSQL_ROOT_PASSWORD: changeme
# MYSQL_DATABASE: mybdd
volumes:
- ./data:/var/lib/mysql
ports:
- 15306:3306
adminer_service:
image: adminer:latest
restart: always
ports:
- 8080:8080
links:
- db_service:db

47
docker-compose.yaml Normal file
View File

@ -0,0 +1,47 @@
version: '3'
services:
karusic_db_service:
image: mysql:latest
restart: always
command: --default-authentication-plugin=mysql_native_password
env_file:
- ./config.env
volumes:
- /workspace/data/karusic/db:/var/lib/mysql
mem_limit: 600m
healthcheck:
test: ["CMD", "mysqladmin" ,"ping", "-h", "localhost"]
timeout: 20s
retries: 10
karauth_adminer_service:
image: adminer:latest
restart: always
depends_on:
- karusic_db_service
ports:
- 19079:8080
links:
- karusic_db_service:db
read_only: false
mem_limit: 100m
# karusic_back_service:
# build: .
# restart: always
# image: org.kar.karusic
# depends_on:
# - karusic_db_service
# ports:
# - 19080:18080
# env_file:
# - ./config.env
# links:
# - karusic_db_service:db
# read_only: true
# mem_limit: 1200m
# healthcheck:
# test: ["CMD", "wget" ,"http://localhost:18080/karusic/api/health_check", "-O", "/dev/null"]
# timeout: 20s
# retries: 3

12
front/.browserslistrc Normal file
View File

@ -0,0 +1,12 @@
# This file is used by the build system to adjust CSS and JS output to support the specified browsers below.
# For additional information regarding the format and rule options, please see:
# https://github.com/browserslist/browserslist#queries
# You can see what browsers were selected by your queries by running:
# npx browserslist
> 0.5%
last 2 versions
Firefox ESR
not dead
not IE 9-11 # For IE 9-11 support, remove 'not'.

13
front/.editorconfig Normal file
View File

@ -0,0 +1,13 @@
# Editor configuration, see http://editorconfig.org
root = true
[*]
charset = utf-8
indent_style = space
indent_size = 2
insert_final_newline = true
trim_trailing_whitespace = true
[*.md]
max_line_length = off
trim_trailing_whitespace = false

4
front/.eslintignore Normal file
View File

@ -0,0 +1,4 @@
node_modules/*
build/*
out/*
dist/*

225
front/.eslintrc.js Normal file
View File

@ -0,0 +1,225 @@
var OFF = 0, WARN = 1, ERROR = 2;
module.exports = {
'env': {
'browser': true,
'es2021': true,
},
'extends': [
'eslint:recommended',
],
'parser': '@typescript-eslint/parser',
'parserOptions': {
'ecmaVersion': 'latest',
'sourceType': 'module',
},
'plugins': [
'@typescript-eslint',
],
"rules": {
// Possible Errors (overrides from recommended set)
"no-extra-parens": ERROR,
"no-unexpected-multiline": ERROR,
// All JSDoc comments must be valid
"valid-jsdoc": [ OFF, {
"requireReturn": false,
"requireReturnDescription": false,
"requireParamDescription": true,
"prefer": {
"return": "returns"
}
}],
// Best Practices
// Allowed a getter without setter, but all setters require getters
"accessor-pairs": [ OFF, {
"getWithoutSet": false,
"setWithoutGet": true
}],
"block-scoped-var": WARN,
"consistent-return": OFF,
"curly": ERROR,
"default-case": WARN,
// the dot goes with the property when doing multiline
"dot-location": [ WARN, "property" ],
"dot-notation": WARN,
"eqeqeq": [ ERROR, "smart" ],
"guard-for-in": WARN,
"no-alert": ERROR,
"no-caller": ERROR,
"no-case-declarations": WARN,
"no-div-regex": WARN,
"no-else-return": WARN,
"no-empty-pattern": WARN,
"no-eq-null": ERROR,
"no-eval": ERROR,
"no-extend-native": ERROR,
"no-extra-bind": WARN,
"no-floating-decimal": WARN,
"no-implicit-coercion": [ WARN, {
"boolean": true,
"number": true,
"string": true
}],
"no-implied-eval": ERROR,
"no-invalid-this": ERROR,
"no-iterator": ERROR,
"no-labels": WARN,
"no-lone-blocks": WARN,
"no-loop-func": ERROR,
"no-magic-numbers": OFF,
"no-multi-spaces": ERROR,
"no-multi-str": WARN,
"no-native-reassign": ERROR,
"no-new-func": ERROR,
"no-new-wrappers": ERROR,
"no-new": ERROR,
"no-octal-escape": ERROR,
"no-param-reassign": ERROR,
"no-process-env": WARN,
"no-proto": ERROR,
"no-redeclare": ERROR,
"no-return-assign": ERROR,
"no-script-url": ERROR,
"no-self-compare": ERROR,
"no-throw-literal": ERROR,
"no-unused-expressions": ERROR,
"no-useless-call": ERROR,
"no-useless-concat": ERROR,
"no-void": WARN,
// Produce warnings when something is commented as TODO or FIXME
"no-warning-comments": [ WARN, {
"terms": [ "TODO", "FIXME" ],
"location": "start"
}],
"no-with": WARN,
"radix": WARN,
"vars-on-top": ERROR,
// Enforces the style of wrapped functions
"wrap-iife": [ ERROR, "outside" ],
"yoda": ERROR,
// Strict Mode - for ES6, never use strict.
"strict": [ ERROR, "never" ],
// Variables
"init-declarations": [ OFF, "always" ],
"no-catch-shadow": WARN,
"no-delete-var": ERROR,
"no-label-var": ERROR,
"no-shadow-restricted-names": ERROR,
"no-shadow": WARN,
// We require all vars to be initialized (see init-declarations)
// If we NEED a var to be initialized to undefined, it needs to be explicit
"no-undef-init": OFF,
"no-undef": ERROR,
"no-undefined": OFF,
"no-unused-vars": OFF,
// Disallow hoisting - let & const don't allow hoisting anyhow
"no-use-before-define": ERROR,
// Node.js and CommonJS
"callback-return": [ WARN, [ "callback", "next" ]],
"global-require": ERROR,
"handle-callback-err": WARN,
"no-mixed-requires": WARN,
"no-new-require": ERROR,
// Use path.concat instead
"no-path-concat": ERROR,
"no-process-exit": ERROR,
"no-restricted-modules": OFF,
"no-sync": WARN,
// ECMAScript 6 support
"arrow-body-style": [ ERROR, "always" ],
"arrow-parens": [ ERROR, "always" ],
"arrow-spacing": [ ERROR, { "before": true, "after": true }],
"constructor-super": ERROR,
"generator-star-spacing": [ ERROR, "before" ],
"no-confusing-arrow": ERROR,
"no-class-assign": ERROR,
"no-const-assign": ERROR,
"no-dupe-class-members": ERROR,
"no-this-before-super": ERROR,
"no-var": WARN,
"object-shorthand": [ WARN, "never" ],
"prefer-arrow-callback": WARN,
"prefer-spread": WARN,
"prefer-template": WARN,
"require-yield": ERROR,
// Stylistic - everything here is a warning because of style.
"array-bracket-spacing": [ WARN, "always" ],
"block-spacing": [ WARN, "always" ],
"brace-style": [ WARN, "1tbs", { "allowSingleLine": false } ],
"camelcase": WARN,
"comma-spacing": [ WARN, { "before": false, "after": true } ],
"comma-style": [ WARN, "last" ],
"computed-property-spacing": [ WARN, "never" ],
"consistent-this": [ WARN, "self" ],
"eol-last": WARN,
"func-names": WARN,
"func-style": [ WARN, "declaration" ],
"id-length": [ WARN, { "min": 2, "max": 32 } ],
"indent": [ WARN, 'tab' ],
"jsx-quotes": [ WARN, "prefer-double" ],
"linebreak-style": [ WARN, "unix" ],
"lines-around-comment": [ OFF, { "beforeBlockComment": true } ],
"max-depth": [ WARN, 8 ],
"max-len": [ WARN, 182 ],
"max-nested-callbacks": [ WARN, 8 ],
"max-params": [ WARN, 10 ],
"new-cap": OFF,
"new-parens": WARN,
"no-array-constructor": WARN,
"no-bitwise": OFF,
"no-continue": OFF,
"no-inline-comments": OFF,
"no-lonely-if": OFF,
"no-mixed-spaces-and-tabs": OFF,
"no-multiple-empty-lines": WARN,
"no-negated-condition": OFF,
"no-nested-ternary": WARN,
"no-new-object": WARN,
"no-plusplus": OFF,
"no-spaced-func": WARN,
"no-ternary": OFF,
"no-trailing-spaces": WARN,
"no-underscore-dangle": WARN,
"no-unneeded-ternary": WARN,
"object-curly-spacing": [ WARN, "always" ],
"one-var": OFF,
"operator-assignment": [ WARN, "never" ],
"operator-linebreak": [ WARN, "after" ],
"padded-blocks": [ WARN, "never" ],
"quote-props": [ WARN, "consistent-as-needed" ],
"quotes": [ WARN, "single" ],
"require-jsdoc": [ OFF, {
"require": {
"FunctionDeclaration": true,
"MethodDefinition": true,
"ClassDeclaration": false
}
}],
"semi-spacing": [ WARN, { "before": false, "after": true }],
"semi": [ ERROR, "always" ],
"sort-vars": OFF,
"keyword-spacing": [WARN, {
"overrides": {
"if": { "after": false },
"for": { "after": false },
"while": { "after": false },
"static": { "after": false },
"as": { "after": false }
}
}],
"space-before-blocks": [ WARN, "always" ],
"space-before-function-paren": [ WARN, "never" ],
"space-in-parens": [ WARN, "never" ],
"space-infix-ops": [ WARN, { "int32Hint": true } ],
"space-unary-ops": ERROR,
"spaced-comment": [ WARN, "always" ],
"wrap-regex": WARN,
},
};

3
front/.gitignore vendored Normal file
View File

@ -0,0 +1,3 @@
/node_modules/
/.angular/
/.idea/

35
front/Dockerfile Normal file
View File

@ -0,0 +1,35 @@
# base image
FROM node:lts as build
# add `/application/node_modules/.bin` to $PATH
ENV PATH /application/node_modules/.bin:$PATH
ADD package-lock.json /application/
ADD package.json /application/
#ADD browserslist /application/
ADD karma.conf.js /application/
ADD protractor.conf.js /application/
WORKDIR /application/
# install and cache app dependencies
RUN npm install
ADD e2e /application/e2e
ADD tsconfig.json /application/
ADD tslint.json /application/
ADD angular.json /application/
ADD src /application/src
# generate build
RUN ng build --output-path=dist --configuration=production --base-href=/karideo/ --deploy-url=/karideo/
############
### prod ###
############
# base image
FROM httpd:latest
# copy artifact build from the 'build environment'
COPY --from=build /application/dist /usr/local/apache2/htdocs/
COPY httpd/httpd.conf /usr/local/apache2/conf/httpd.conf

24
front/Dockerfile.dev Normal file
View File

@ -0,0 +1,24 @@
# base image
FROM node:latest
ADD src /application/src
ADD e2e /application/e2e
ADD package-lock.json /application/
ADD package.json /application/
ADD angular.json /application/
ADD browserslist /application/
ADD karma.conf.js /application/
ADD protractor.conf.js /application/
ADD tsconfig.json /application/
ADD tslint.json /application/
WORKDIR /application/
# add `/app/node_modules/.bin` to $PATH
ENV PATH /app/node_modules/.bin:$PATH
# install and cache app dependencies
RUN npm install
# start app
CMD ["npx", "ng", "serve", "--host", "0.0.0.0"]

121
front/angular.json Normal file
View File

@ -0,0 +1,121 @@
{
"$schema" : "./node_modules/@angular/cli/lib/config/schema.json",
"version" : 1,
"newProjectRoot" : "projects",
"defaultProject" : "karusic",
"projects" : {
"karusic" : {
"root" : "",
"sourceRoot" : "src",
"projectType" : "application",
"architect" : {
"build" : {
"builder" : "@angular-devkit/build-angular:browser",
"options" : {
"outputPath" : "dist",
"index" : "src/index.html",
"main" : "src/main.ts",
"tsConfig" : "src/tsconfig.app.json",
"polyfills" : "src/polyfills.ts",
"assets" : [ "src/assets", "src/favicon.ico" ],
"styles" : [ "src/styles.less", "src/generic_page.less", "src/theme.color.blue.less", "src/theme.checkbox.less", "src/theme.modal.less" ],
"scripts" : [ ]
},
"configurations" : {
"production" : {
"optimization" : true,
"outputHashing" : "all",
"sourceMap" : false,
"namedChunks" : false,
"aot" : true,
"extractLicenses" : true,
"vendorChunk" : false,
"buildOptimizer" : true,
"fileReplacements" : [ {
"replace" : "src/environments/environment.ts",
"with" : "src/environments/environment.prod.ts"
} ]
}
}
},
"serve" : {
"builder" : "@angular-devkit/build-angular:dev-server",
"options" : {
"browserTarget" : "karusic:build"
},
"configurations" : {
"production" : {
"browserTarget" : "karusic:build:production"
}
}
},
"extract-i18n" : {
"builder" : "@angular-devkit/build-angular:extract-i18n",
"options" : {
"browserTarget" : "karusic:build"
}
},
"test" : {
"builder" : "@angular-devkit/build-angular:karma",
"options" : {
"main" : "src/test.ts",
"karmaConfig" : "./karma.conf.js",
"polyfills" : "src/polyfills.ts",
"tsConfig" : "src/tsconfig.spec.json",
"scripts" : [ ],
"styles" : [ "src/styles.less", "src/generic_page.less", "src/theme.color.blue.less", "src/theme.checkbox.less", "src/theme.modal.less" ],
"assets" : [ "src/assets", "src/favicon.ico" ]
}
},
"lint" : {
"builder" : "@angular-eslint/builder:lint",
"options" : {
"fix": true,
"eslintConfig": ".eslintrc.js",
"lintFilePatterns": [
"src/**/*.spec.ts",
"src/**/*.ts"
]
}
},
"TTTTTTlint" : {
"builder" : "@angular-devkit/build-angular:tslint",
"options" : {
"tsConfig" : [ "src/tsconfig.app.json", "src/tsconfig.spec.json" ],
"exclude" : [ "**/node_modules/**" ]
}
}
}
},
"karusic-e2e" : {
"root" : "e2e",
"sourceRoot" : "e2e",
"projectType" : "application",
"architect" : {
"e2e" : {
"builder" : "@angular-devkit/build-angular:protractor",
"options" : {
"protractorConfig" : "./protractor.conf.js",
"devServerTarget" : "karusic:serve"
}
},
"lint" : {
"builder" : "@angular-devkit/build-angular:tslint",
"options" : {
"tsConfig" : [ "e2e/tsconfig.e2e.json" ],
"exclude" : [ "**/node_modules/**" ]
}
}
}
}
},
"schematics" : {
"@schematics/angular:component" : {
"prefix" : "app",
"style" : "less"
},
"@schematics/angular:directive" : {
"prefix" : "app"
}
}
}

11
front/docker-compose.yaml Executable file
View File

@ -0,0 +1,11 @@
version: '3'
services:
karideo_service:
build: .
restart: always
image: yui.heero/karideo
container_name: karideo
ports:
#- 15081:4200
- 15081:80

14
front/e2e/app.e2e-spec.ts Normal file
View File

@ -0,0 +1,14 @@
import { AppPage } from './app.po';
describe('karusic App', () => {
let page: AppPage;
beforeEach(() => {
page = new AppPage();
});
it('should display welcome message', () => {
page.navigateTo();
expect(page.getParagraphText()).toEqual('Welcome to app!');
});
});

11
front/e2e/app.po.ts Normal file
View File

@ -0,0 +1,11 @@
import { browser, by, element } from 'protractor';
export class AppPage {
navigateTo() {
return browser.get('/');
}
getParagraphText() {
return element(by.css('app-root h1')).getText();
}
}

View File

@ -0,0 +1,14 @@
{
"extends": "../tsconfig.json",
"compilerOptions": {
"outDir": "../out-tsc/e2e",
"baseUrl": "./",
"module": "commonjs",
"target": "es5",
"types": [
"jasmine",
"jasminewd2",
"node"
]
}
}

541
front/httpd/httpd.conf Normal file
View File

@ -0,0 +1,541 @@
#
# This is the main Apache HTTP server configuration file. It contains the
# configuration directives that give the server its instructions.
# See <URL:http://httpd.apache.org/docs/2.4/> for detailed information.
# In particular, see
# <URL:http://httpd.apache.org/docs/2.4/mod/directives.html>
# for a discussion of each configuration directive.
#
# Do NOT simply read the instructions in here without understanding
# what they do. They're here only as hints or reminders. If you are unsure
# consult the online docs. You have been warned.
#
# Configuration and logfile names: If the filenames you specify for many
# of the server's control files begin with "/" (or "drive:/" for Win32), the
# server will use that explicit path. If the filenames do *not* begin
# with "/", the value of ServerRoot is prepended -- so "logs/access_log"
# with ServerRoot set to "/usr/local/apache2" will be interpreted by the
# server as "/usr/local/apache2/logs/access_log", whereas "/logs/access_log"
# will be interpreted as '/logs/access_log'.
#
# ServerRoot: The top of the directory tree under which the server's
# configuration, error, and log files are kept.
#
# Do not add a slash at the end of the directory path. If you point
# ServerRoot at a non-local disk, be sure to specify a local disk on the
# Mutex directive, if file-based mutexes are used. If you wish to share the
# same ServerRoot for multiple httpd daemons, you will need to change at
# least PidFile.
#
ServerRoot "/usr/local/apache2"
#
# Mutex: Allows you to set the mutex mechanism and mutex file directory
# for individual mutexes, or change the global defaults
#
# Uncomment and change the directory if mutexes are file-based and the default
# mutex file directory is not on a local disk or is not appropriate for some
# other reason.
#
# Mutex default:logs
#
# Listen: Allows you to bind Apache to specific IP addresses and/or
# ports, instead of the default. See also the <VirtualHost>
# directive.
#
# Change this to Listen on specific IP addresses as shown below to
# prevent Apache from glomming onto all bound IP addresses.
#
Listen 80
Listen 443
#
# Dynamic Shared Object (DSO) Support
#
# To be able to use the functionality of a module which was built as a DSO you
# have to place corresponding `LoadModule' lines at this location so the
# directives contained in it are actually available _before_ they are used.
# Statically compiled modules (those listed by `httpd -l') do not need
# to be loaded here.
#
# Example:
# LoadModule foo_module modules/mod_foo.so
#
LoadModule mpm_event_module modules/mod_mpm_event.so
#LoadModule mpm_prefork_module modules/mod_mpm_prefork.so
#LoadModule mpm_worker_module modules/mod_mpm_worker.so
LoadModule authn_file_module modules/mod_authn_file.so
#LoadModule authn_dbm_module modules/mod_authn_dbm.so
#LoadModule authn_anon_module modules/mod_authn_anon.so
#LoadModule authn_dbd_module modules/mod_authn_dbd.so
#LoadModule authn_socache_module modules/mod_authn_socache.so
LoadModule authn_core_module modules/mod_authn_core.so
LoadModule authz_host_module modules/mod_authz_host.so
LoadModule authz_groupfile_module modules/mod_authz_groupfile.so
LoadModule authz_user_module modules/mod_authz_user.so
#LoadModule authz_dbm_module modules/mod_authz_dbm.so
#LoadModule authz_owner_module modules/mod_authz_owner.so
#LoadModule authz_dbd_module modules/mod_authz_dbd.so
LoadModule authz_core_module modules/mod_authz_core.so
#LoadModule authnz_ldap_module modules/mod_authnz_ldap.so
#LoadModule authnz_fcgi_module modules/mod_authnz_fcgi.so
LoadModule access_compat_module modules/mod_access_compat.so
LoadModule auth_basic_module modules/mod_auth_basic.so
#LoadModule auth_form_module modules/mod_auth_form.so
#LoadModule auth_digest_module modules/mod_auth_digest.so
#LoadModule allowmethods_module modules/mod_allowmethods.so
#LoadModule isapi_module modules/mod_isapi.so
#LoadModule file_cache_module modules/mod_file_cache.so
#LoadModule cache_module modules/mod_cache.so
#LoadModule cache_disk_module modules/mod_cache_disk.so
#LoadModule cache_socache_module modules/mod_cache_socache.so
#LoadModule socache_shmcb_module modules/mod_socache_shmcb.so
#LoadModule socache_dbm_module modules/mod_socache_dbm.so
#LoadModule socache_memcache_module modules/mod_socache_memcache.so
#LoadModule watchdog_module modules/mod_watchdog.so
#LoadModule macro_module modules/mod_macro.so
#LoadModule dbd_module modules/mod_dbd.so
#LoadModule bucketeer_module modules/mod_bucketeer.so
#LoadModule dumpio_module modules/mod_dumpio.so
#LoadModule echo_module modules/mod_echo.so
#LoadModule example_hooks_module modules/mod_example_hooks.so
#LoadModule case_filter_module modules/mod_case_filter.so
#LoadModule case_filter_in_module modules/mod_case_filter_in.so
#LoadModule example_ipc_module modules/mod_example_ipc.so
#LoadModule buffer_module modules/mod_buffer.so
#LoadModule data_module modules/mod_data.so
#LoadModule ratelimit_module modules/mod_ratelimit.so
LoadModule reqtimeout_module modules/mod_reqtimeout.so
#LoadModule ext_filter_module modules/mod_ext_filter.so
#LoadModule request_module modules/mod_request.so
#LoadModule include_module modules/mod_include.so
LoadModule filter_module modules/mod_filter.so
#LoadModule reflector_module modules/mod_reflector.so
#LoadModule substitute_module modules/mod_substitute.so
#LoadModule sed_module modules/mod_sed.so
#LoadModule charset_lite_module modules/mod_charset_lite.so
#LoadModule deflate_module modules/mod_deflate.so
LoadModule xml2enc_module modules/mod_xml2enc.so
LoadModule proxy_html_module modules/mod_proxy_html.so
LoadModule mime_module modules/mod_mime.so
#LoadModule ldap_module modules/mod_ldap.so
LoadModule log_config_module modules/mod_log_config.so
#LoadModule log_debug_module modules/mod_log_debug.so
#LoadModule log_forensic_module modules/mod_log_forensic.so
#LoadModule logio_module modules/mod_logio.so
#LoadModule lua_module modules/mod_lua.so
LoadModule env_module modules/mod_env.so
#LoadModule mime_magic_module modules/mod_mime_magic.so
#LoadModule cern_meta_module modules/mod_cern_meta.so
#LoadModule expires_module modules/mod_expires.so
LoadModule headers_module modules/mod_headers.so
#LoadModule ident_module modules/mod_ident.so
#LoadModule usertrack_module modules/mod_usertrack.so
#LoadModule unique_id_module modules/mod_unique_id.so
LoadModule setenvif_module modules/mod_setenvif.so
LoadModule version_module modules/mod_version.so
#LoadModule remoteip_module modules/mod_remoteip.so
LoadModule proxy_module modules/mod_proxy.so
#LoadModule proxy_connect_module modules/mod_proxy_connect.so
#LoadModule proxy_ftp_module modules/mod_proxy_ftp.so
LoadModule proxy_http_module modules/mod_proxy_http.so
#LoadModule proxy_fcgi_module modules/mod_proxy_fcgi.so
#LoadModule proxy_scgi_module modules/mod_proxy_scgi.so
#LoadModule proxy_uwsgi_module modules/mod_proxy_uwsgi.so
#LoadModule proxy_fdpass_module modules/mod_proxy_fdpass.so
#LoadModule proxy_wstunnel_module modules/mod_proxy_wstunnel.so
#LoadModule proxy_ajp_module modules/mod_proxy_ajp.so
#LoadModule proxy_balancer_module modules/mod_proxy_balancer.so
#LoadModule proxy_express_module modules/mod_proxy_express.so
#LoadModule proxy_hcheck_module modules/mod_proxy_hcheck.so
#LoadModule session_module modules/mod_session.so
#LoadModule session_cookie_module modules/mod_session_cookie.so
#LoadModule session_crypto_module modules/mod_session_crypto.so
#LoadModule session_dbd_module modules/mod_session_dbd.so
#LoadModule slotmem_shm_module modules/mod_slotmem_shm.so
#LoadModule slotmem_plain_module modules/mod_slotmem_plain.so
LoadModule ssl_module modules/mod_ssl.so
#LoadModule optional_hook_export_module modules/mod_optional_hook_export.so
#LoadModule optional_hook_import_module modules/mod_optional_hook_import.so
#LoadModule optional_fn_import_module modules/mod_optional_fn_import.so
#LoadModule optional_fn_export_module modules/mod_optional_fn_export.so
#LoadModule dialup_module modules/mod_dialup.so
#LoadModule http2_module modules/mod_http2.so
#LoadModule proxy_http2_module modules/mod_proxy_http2.so
#LoadModule lbmethod_byrequests_module modules/mod_lbmethod_byrequests.so
#LoadModule lbmethod_bytraffic_module modules/mod_lbmethod_bytraffic.so
#LoadModule lbmethod_bybusyness_module modules/mod_lbmethod_bybusyness.so
#LoadModule lbmethod_heartbeat_module modules/mod_lbmethod_heartbeat.so
LoadModule unixd_module modules/mod_unixd.so
#LoadModule heartbeat_module modules/mod_heartbeat.so
#LoadModule heartmonitor_module modules/mod_heartmonitor.so
#LoadModule dav_module modules/mod_dav.so
LoadModule status_module modules/mod_status.so
LoadModule autoindex_module modules/mod_autoindex.so
#LoadModule asis_module modules/mod_asis.so
#LoadModule info_module modules/mod_info.so
#LoadModule suexec_module modules/mod_suexec.so
<IfModule !mpm_prefork_module>
#LoadModule cgid_module modules/mod_cgid.so
</IfModule>
<IfModule mpm_prefork_module>
#LoadModule cgi_module modules/mod_cgi.so
</IfModule>
#LoadModule dav_fs_module modules/mod_dav_fs.so
#LoadModule dav_lock_module modules/mod_dav_lock.so
#LoadModule vhost_alias_module modules/mod_vhost_alias.so
#LoadModule negotiation_module modules/mod_negotiation.so
LoadModule dir_module modules/mod_dir.so
#LoadModule imagemap_module modules/mod_imagemap.so
#LoadModule actions_module modules/mod_actions.so
#LoadModule speling_module modules/mod_speling.so
#LoadModule userdir_module modules/mod_userdir.so
LoadModule alias_module modules/mod_alias.so
LoadModule rewrite_module modules/mod_rewrite.so
<IfModule unixd_module>
#
# If you wish httpd to run as a different user or group, you must run
# httpd as root initially and it will switch.
#
# User/Group: The name (or #number) of the user/group to run httpd as.
# It is usually good practice to create a dedicated user and group for
# running httpd, as with most system services.
#
User daemon
Group daemon
</IfModule>
# 'Main' server configuration
#
# The directives in this section set up the values used by the 'main'
# server, which responds to any requests that aren't handled by a
# <VirtualHost> definition. These values also provide defaults for
# any <VirtualHost> containers you may define later in the file.
#
# All of these directives may appear inside <VirtualHost> containers,
# in which case these default settings will be overridden for the
# virtual host being defined.
#
#
# ServerAdmin: Your address, where problems with the server should be
# e-mailed. This address appears on some server-generated pages, such
# as error documents. e.g. admin@your-domain.com
#
ServerAdmin yui.heero@gmail.com
#
# ServerName gives the name and port that the server uses to identify itself.
# This can often be determined automatically, but we recommend you specify
# it explicitly to prevent problems during startup.
#
# If your host doesn't have a registered DNS name, enter its IP address here.
#
#ServerName www.example.com:80
#
# Deny access to the entirety of your server's filesystem. You must
# explicitly permit access to web content directories in other
# <Directory> blocks below.
#
<Directory />
AllowOverride none
Require all denied
</Directory>
# intermediate configuration, tweak to your needs
SSLProtocol all -SSLv2 -SSLv3
SSLCipherSuite ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA:ECDHE-RSA-AES256-SHA:DHE-RSA-AES128-SHA256:DHE-RSA-AES128-SHA:DHE-RSA-AES256-SHA256:DHE-RSA-AES256-SHA:ECDHE-ECDSA-DES-CBC3-SHA:ECDHE-RSA-DES-CBC3-SHA:EDH-RSA-DES-CBC3-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA256:AES256-SHA256:AES128-SHA:AES256-SHA:DES-CBC3-SHA:!DSS
SSLHonorCipherOrder on
#
# Note that from this point forward you must specifically allow
# particular features to be enabled - so if something's not working as
# you might expect, make sure that you have specifically enabled it
# below.
#
#
# DocumentRoot: The directory out of which you will serve your
# documents. By default, all requests are taken from this directory, but
# symbolic links and aliases may be used to point to other locations.
#
<VirtualHost *:80>
ServerName my-app
DocumentRoot "/usr/local/apache2/htdocs"
<Directory "/usr/local/apache2/htdocs">
Options Indexes FollowSymLinks
AllowOverride None
Require all granted
RewriteEngine on
# Don't rewrite files or directories
RewriteCond %{REQUEST_FILENAME} -f [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^ - [L]
# Rewrite everything else to index.html to allow HTML5 state links
RewriteRule ^ index.html [L]
</Directory>
</VirtualHost>
#
# DirectoryIndex: sets the file that Apache will serve if a directory
# is requested.
#
<IfModule dir_module>
DirectoryIndex index.html
</IfModule>
#
# The following lines prevent .htaccess and .htpasswd files from being
# viewed by Web clients.
#
<Files ".ht*">
Require all denied
</Files>
#
# ErrorLog: The location of the error log file.
# If you do not specify an ErrorLog directive within a <VirtualHost>
# container, error messages relating to that virtual host will be
# logged here. If you *do* define an error logfile for a <VirtualHost>
# container, that host's errors will be logged there and not here.
#
ErrorLog /proc/self/fd/2
#
# LogLevel: Control the number of messages logged to the error_log.
# Possible values include: debug, info, notice, warn, error, crit,
# alert, emerg.
#
LogLevel warn
<IfModule log_config_module>
#
# The following directives define some format nicknames for use with
# a CustomLog directive (see below).
#
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined
LogFormat "%h %l %u %t \"%r\" %>s %b" common
<IfModule logio_module>
# You need to enable mod_logio.c to use %I and %O
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\" %I %O" combinedio
</IfModule>
#
# The location and format of the access logfile (Common Logfile Format).
# If you do not define any access logfiles within a <VirtualHost>
# container, they will be logged here. Contrariwise, if you *do*
# define per-<VirtualHost> access logfiles, transactions will be
# logged therein and *not* in this file.
#
CustomLog /proc/self/fd/1 common
#
# If you prefer a logfile with access, agent, and referer information
# (Combined Logfile Format) you can use the following directive.
#
#CustomLog "logs/access_log" combined
</IfModule>
<IfModule alias_module>
#
# Redirect: Allows you to tell clients about documents that used to
# exist in your server's namespace, but do not anymore. The client
# will make a new request for the document at its new location.
# Example:
# Redirect permanent /foo http://www.example.com/bar
#
# Alias: Maps web paths into filesystem paths and is used to
# access content that does not live under the DocumentRoot.
# Example:
# Alias /webpath /full/filesystem/path
#
# If you include a trailing / on /webpath then the server will
# require it to be present in the URL. You will also likely
# need to provide a <Directory> section to allow access to
# the filesystem path.
#
# ScriptAlias: This controls which directories contain server scripts.
# ScriptAliases are essentially the same as Aliases, except that
# documents in the target directory are treated as applications and
# run by the server when requested rather than as documents sent to the
# client. The same rules about trailing "/" apply to ScriptAlias
# directives as to Alias.
#
ScriptAlias /cgi-bin/ "/usr/local/apache2/cgi-bin/"
</IfModule>
<IfModule cgid_module>
#
# ScriptSock: On threaded servers, designate the path to the UNIX
# socket used to communicate with the CGI daemon of mod_cgid.
#
#Scriptsock cgisock
</IfModule>
#
# "/usr/local/apache2/cgi-bin" should be changed to whatever your ScriptAliased
# CGI directory exists, if you have that configured.
#
<Directory "/usr/local/apache2/cgi-bin">
AllowOverride None
Options None
Require all granted
</Directory>
<IfModule headers_module>
#
# Avoid passing HTTP_PROXY environment to CGI's on this or any proxied
# backend servers which have lingering "httpoxy" defects.
# 'Proxy' request header is undefined by the IETF, not listed by IANA
#
RequestHeader unset Proxy early
</IfModule>
<IfModule mime_module>
#
# TypesConfig points to the file containing the list of mappings from
# filename extension to MIME-type.
#
TypesConfig conf/mime.types
#
# AddType allows you to add to or override the MIME configuration
# file specified in TypesConfig for specific file types.
#
#AddType application/x-gzip .tgz
#
# AddEncoding allows you to have certain browsers uncompress
# information on the fly. Note: Not all browsers support this.
#
#AddEncoding x-compress .Z
#AddEncoding x-gzip .gz .tgz
#
# If the AddEncoding directives above are commented-out, then you
# probably should define those extensions to indicate media types:
#
AddType application/x-compress .Z
AddType application/x-gzip .gz .tgz
#
# AddHandler allows you to map certain file extensions to "handlers":
# actions unrelated to filetype. These can be either built into the server
# or added with the Action directive (see below)
#
# To use CGI scripts outside of ScriptAliased directories:
# (You will also need to add "ExecCGI" to the "Options" directive.)
#
#AddHandler cgi-script .cgi
# For type maps (negotiated resources):
#AddHandler type-map var
#
# Filters allow you to process content before it is sent to the client.
#
# To parse .shtml files for server-side includes (SSI):
# (You will also need to add "Includes" to the "Options" directive.)
#
#AddType text/html .shtml
#AddOutputFilter INCLUDES .shtml
</IfModule>
#
# The mod_mime_magic module allows the server to use various hints from the
# contents of the file itself to determine its type. The MIMEMagicFile
# directive tells the module where the hint definitions are located.
#
#MIMEMagicFile conf/magic
#
# Customizable error responses come in three flavors:
# 1) plain text 2) local redirects 3) external redirects
#
# Some examples:
#ErrorDocument 500 "The server made a boo boo."
#ErrorDocument 404 /missing.html
#ErrorDocument 404 "/cgi-bin/missing_handler.pl"
#ErrorDocument 402 http://www.example.com/subscription_info.html
#
#
# MaxRanges: Maximum number of Ranges in a request before
# returning the entire resource, or one of the special
# values 'default', 'none' or 'unlimited'.
# Default setting is to accept 200 Ranges.
#MaxRanges unlimited
#
# EnableMMAP and EnableSendfile: On systems that support it,
# memory-mapping or the sendfile syscall may be used to deliver
# files. This usually improves server performance, but must
# be turned off when serving from networked-mounted
# filesystems or if support for these functions is otherwise
# broken on your system.
# Defaults: EnableMMAP On, EnableSendfile Off
#
#EnableMMAP off
#EnableSendfile on
# Supplemental configuration
#
# The configuration files in the conf/extra/ directory can be
# included to add extra features or to modify the default configuration of
# the server, or you may simply copy their contents here and change as
# necessary.
# Server-pool management (MPM specific)
#Include conf/extra/httpd-mpm.conf
# Multi-language error messages
#Include conf/extra/httpd-multilang-errordoc.conf
# Fancy directory listings
#Include conf/extra/httpd-autoindex.conf
# Language settings
#Include conf/extra/httpd-languages.conf
# User home directories
#Include conf/extra/httpd-userdir.conf
# Real-time info on requests and configuration
#Include conf/extra/httpd-info.conf
# Virtual hosts
#Include conf/extra/httpd-vhosts.conf
# Local access to the Apache HTTP Server Manual
#Include conf/extra/httpd-manual.conf
# Distributed authoring and versioning (WebDAV)
#Include conf/extra/httpd-dav.conf
# Various default settings
#Include conf/extra/httpd-default.conf
# Configure mod_proxy_html to understand HTML4/XHTML1
<IfModule proxy_html_module>
Include conf/extra/proxy-html.conf
</IfModule>
# Secure (SSL/TLS) connections
#Include conf/extra/httpd-ssl.conf
#
# Note: The following must must be present to support
# starting without SSL on platforms with no /dev/random equivalent
# but a statically compiled-in mod_ssl.
#
<IfModule ssl_module>
SSLRandomSeed startup builtin
SSLRandomSeed connect builtin
</IfModule>

31
front/karma.conf.js Normal file
View File

@ -0,0 +1,31 @@
// Karma configuration file, see link for more information
// https://karma-runner.github.io/1.0/config/configuration-file.html
module.exports = function (config) {
config.set({
basePath: '',
frameworks: ['jasmine', '@angular-devkit/build-angular'],
plugins: [
require('karma-jasmine'),
require('karma-chrome-launcher'),
require('karma-jasmine-html-reporter'),
require('karma-coverage-istanbul-reporter'),
require('@angular-devkit/build-angular/plugins/karma')
],
client:{
clearContext: false // leave Jasmine Spec Runner output visible in browser
},
coverageIstanbulReporter: {
dir: require('path').join(__dirname, 'coverage'), reports: [ 'html', 'lcovonly' ],
fixWebpackSourcePaths: true
},
reporters: ['progress', 'kjhtml'],
port: 9876,
colors: true,
logLevel: config.LOG_INFO,
autoWatch: true,
browsers: ['Chrome'],
singleRun: false
});
};

27257
front/package-lock.json generated Normal file

File diff suppressed because it is too large Load Diff

63
front/package.json Normal file
View File

@ -0,0 +1,63 @@
{
"name": "karusic",
"version": "0.0.0",
"license": "MIT",
"scripts": {
"all": "npm run build && npm run test",
"ng": "ng",
"start": "ng serve --watch",
"build": "ng build --prod",
"test": "ng test",
"lint": "ng lint",
"e2e": "ng e2e"
},
"private": true,
"dependencies": {
"@angular/animations": "^13.2.5",
"@angular/cdk": "^13.2.5",
"@angular/common": "^13.2.5",
"@angular/compiler": "^13.2.5",
"@angular/core": "^13.2.5",
"@angular/forms": "^13.2.5",
"@angular/material": "^13.2.5",
"@angular/platform-browser": "^13.2.5",
"@angular/platform-browser-dynamic": "^13.2.5",
"@angular/router": "^13.2.5",
"core-js": "^3.21.1",
"jquery": "^3.6.0",
"rxjs": "^7.5.4",
"tslib": "^2.3.1",
"videogular": "^2.2.1",
"zone.js": "^0.11.5"
},
"devDependencies": {
"@angular-devkit/build-angular": "^13.2.5",
"@angular-eslint/builder": "13.1.0",
"@angular-eslint/eslint-plugin": "13.1.0",
"@angular-eslint/eslint-plugin-template": "13.1.0",
"@angular-eslint/schematics": "13.1.0",
"@angular-eslint/template-parser": "13.1.0",
"@angular/cli": "^13.2.5",
"@angular/compiler-cli": "^13.2.5",
"@angular/language-service": "^13.2.5",
"@types/jasmine": "^3.10.3",
"@types/jasminewd2": "^2.0.10",
"@types/node": "^17.0.21",
"@typescript-eslint/eslint-plugin": "^5.17.0",
"@typescript-eslint/parser": "^5.17.0",
"codelyzer": "^6.0.2",
"eslint": "^8.12.0",
"eslint-config-google": "^0.14.0",
"jasmine-core": "^4.0.1",
"jasmine-spec-reporter": "^7.0.0",
"karma": "^6.3.17",
"karma-chrome-launcher": "^3.1.0",
"karma-coverage-istanbul-reporter": "^3.0.3",
"karma-jasmine": "^4.0.1",
"karma-jasmine-html-reporter": "^1.7.0",
"protractor": "^7.0.0",
"ts-node": "^10.7.0",
"tslint": "^5.20.1",
"typescript": "~4.5.5"
}
}

28
front/protractor.conf.js Normal file
View File

@ -0,0 +1,28 @@
// Protractor configuration file, see link for more information
// https://github.com/angular/protractor/blob/master/lib/config.ts
const { SpecReporter } = require('jasmine-spec-reporter');
exports.config = {
allScriptsTimeout: 11000,
specs: [
'./e2e/**/*.e2e-spec.ts'
],
capabilities: {
'browserName': 'chrome'
},
directConnect: true,
baseUrl: 'http://localhost:4200/',
framework: 'jasmine',
jasmineNodeOpts: {
showColors: true,
defaultTimeoutInterval: 30000,
print: function() {}
},
onPrepare() {
require('ts-node').register({
project: 'e2e/tsconfig.e2e.json'
});
jasmine.getEnv().addReporter(new SpecReporter({ spec: { displayStacktrace: true } }));
}
};

34
front/readme.md Normal file
View File

@ -0,0 +1,34 @@
Start the application:
```
npm install
```
upgrade package
```
npm audit fix
```
## npm install -g angular-cli
start the application:
```
npx ng serve --watch
```
plus facilement:
npm install @angular-devkit/build-angular@0.901.9
npm start
Apply linter:
==============
```
npx ng lint
```

View File

@ -0,0 +1,47 @@
/** @file
* @author Edouard DUPIN
* @copyright 2018, Edouard DUPIN, all right reserved
* @license PROPRIETARY (see license file)
*/
import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router'; // CLI imports router
import { HelpScene, HomeScene, SeasonEditScene, SeasonScene, SeriesEditScene, SeriesScene, SettingsScene, SsoScene, TypeScene, UniverseScene, UploadScene, VideoEditScene, VideoScene } from './scene';
// import { HelpComponent } from './help/help.component';
// see https://angular.io/guide/router
const routes: Routes = [
{ path: '', redirectTo: '/home', pathMatch: 'full' },
{ path: 'home', component: HomeScene },
{ path: 'upload', component: UploadScene },
{ path: 'type/:universeId/:typeId/:seriesId/:seasonId/:videoId', component: TypeScene },
{ path: 'universe/:universeId/:typeId/:seriesId/:seasonId/:videoId', component: UniverseScene },
{ path: 'series/:universeId/:typeId/:seriesId/:seasonId/:videoId', component: SeriesScene },
{ path: 'series-edit/:universeId/:typeId/:seriesId/:seasonId/:videoId', component: SeriesEditScene },
{ path: 'season/:universeId/:typeId/:seriesId/:seasonId/:videoId', component: SeasonScene },
{ path: 'season-edit/:universeId/:typeId/:seriesId/:seasonId/:videoId', component: SeasonEditScene },
{ path: 'video/:universeId/:typeId/:seriesId/:seasonId/:videoId', component: VideoScene },
{ path: 'video-edit/:universeId/:typeId/:seriesId/:seasonId/:videoId', component: VideoEditScene },
{ path: 'sso/:data/:keepConnected/:token', component: SsoScene },
{ path: 'sso', component: SsoScene },
{ path: 'help/:page', component: HelpScene },
{ path: 'help', component: HelpScene },
{ path: 'settings', component: SettingsScene },
];
@NgModule({
imports: [ RouterModule.forRoot(routes, { relativeLinkResolution: 'legacy' }) ],
exports: [ RouterModule ]
})
export class AppRoutingModule { }
// export const routing: ModuleWithProviders = RouterModule.forRoot(routes);

View File

@ -0,0 +1,10 @@
<!-- exercice section -->
<app-top-menu></app-top-menu>
<!--
<div class="main-content" ng-include="currentDisplay" ng-if="currentDisplay != ''"></div>
<div class="main-modal" ng-include="currentModal" ng-if="currentModal != ''" ></div> <!-- (click)="onOutModal()" -->
-->
<div class="main-content">
<router-outlet *ngIf="autoConnectedDone"></router-outlet>
</div>

View File

@ -0,0 +1,46 @@
#create-exercice-button {
position: fixed;
display: block;
right: 0;
bottom: 0;
margin-right: 40px;
margin-bottom: 40px;
z-index: 900;
}
#save-exercice-button {
position: fixed;
display: block;
right: 0;
bottom: 0;
margin-right: 110px;
margin-bottom: 40px;
z-index: 900;
}
.main-content {
position: absolute;
//width: ~"calc(calc(100% / 5 ) * 5)";
width: 100%;
height: ~"calc(100% - 56px)";
top: 56px;
left: 0;
margin: 0;
padding: 0;
display: block;
position: fixed;
overflow-y: auto;
//background-color:#FF0;
/*
.main-reduce {
width: 40%;
height: 100%;
margin: 0;
padding: 0px 10% 0px 10%;
display: block;
overflow-y:scroll;
}
*/
}

View File

@ -0,0 +1,45 @@
/** @file
* @author Edouard DUPIN
* @copyright 2018, Edouard DUPIN, all right reserved
* @license PROPRIETARY (see license file)
*/
import { Component, OnInit } from '@angular/core';
import { ActivatedRoute, Router } from '@angular/router';
import { UserService, SessionService } from './service';
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: [
'./app.component.less',
]
})
export class AppComponent implements OnInit {
title: string = 'Karideo';
autoConnectedDone: boolean = false;
isConnected: boolean = false;
constructor(
private router: Router,
private userService: UserService,
private sessionService: SessionService) {
}
ngOnInit() {
this.autoConnectedDone = false;
this.isConnected = false;
let self = this;
this.sessionService.change.subscribe((isConnected) => {
console.log(`receive event from session ...${ isConnected}`);
self.isConnected = isConnected;
self.autoConnectedDone = true;
});
this.userService.checkAutoConnect().finally(() => {
self.autoConnectedDone = true;
});
}
}

114
front/src/app/app.module.ts Normal file
View File

@ -0,0 +1,114 @@
/** @file
* @author Edouard DUPIN
* @copyright 2018, Edouard DUPIN, all right reserved
* @license PROPRIETARY (see license file)
*/
import { BrowserModule } from '@angular/platform-browser';
import { NgModule, CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
import { RouterModule } from '@angular/router';
import { HttpClientModule } from '@angular/common/http';
import { FormsModule, ReactiveFormsModule } from '@angular/forms'; // this is needed for dynamic selection of the select
import { AppRoutingModule } from './app-routing.module';
import { UploadFileComponent } from './component/upload-file/upload-file';
import { TopMenuComponent } from './component/top-menu/top-menu';
import { ElementDataImageComponent } from './component/data-image/data-image';
import { ElementTypeComponent } from './component/element-type/element-type';
import { ElementSeriesComponent } from './component/element-series/element-series';
import { ElementSeasonComponent } from './component/element-season/element-season';
import { ElementVideoComponent } from './component/element-video/element-video';
import { PopInComponent } from './component/popin/popin';
import { PopInCreateType } from './popin/create-type/create-type';
import { PopInUploadProgress } from './popin/upload-progress/upload-progress';
import { PopInDeleteConfirm } from './popin/delete-confirm/delete-confirm';
import { AppComponent } from './app.component';
import { ErrorComponent } from './error/error';
import { HomeScene, ErrorViewerScene, HelpScene, SsoScene, TypeScene, UniverseScene, SeriesScene, SeasonScene, VideoScene, SettingsScene,
VideoEditScene, SeasonEditScene, SeriesEditScene, UploadScene } from './scene';
import { PopInService, HttpWrapperService, SessionService, CookiesService, StorageService, UserService, SSOService, BddService, TypeService,
DataService, UniverseService, SeriesService, SeasonService, VideoService, ArianeService } from './service';
@NgModule({
declarations: [
AppComponent,
TopMenuComponent,
UploadFileComponent,
ElementDataImageComponent,
ElementTypeComponent,
ElementSeriesComponent,
ElementSeasonComponent,
ElementVideoComponent,
ErrorComponent,
PopInComponent,
PopInCreateType,
PopInUploadProgress,
PopInDeleteConfirm,
HomeScene,
ErrorViewerScene,
HelpScene,
SsoScene,
TypeScene,
UniverseScene,
SeriesScene,
SeasonScene,
VideoScene,
SettingsScene,
VideoEditScene,
SeasonEditScene,
SeriesEditScene,
UploadScene,
],
imports: [
BrowserModule,
RouterModule,
AppRoutingModule,
HttpClientModule,
FormsModule,
ReactiveFormsModule,
],
providers: [
PopInService,
HttpWrapperService,
SessionService,
CookiesService,
StorageService,
UserService,
SSOService,
BddService,
TypeService,
DataService,
UniverseService,
SeriesService,
SeasonService,
VideoService,
ArianeService
],
exports: [
AppComponent,
TopMenuComponent,
UploadFileComponent,
ErrorComponent,
ElementTypeComponent,
ElementSeriesComponent,
ElementSeasonComponent,
ElementVideoComponent,
PopInCreateType,
PopInComponent,
PopInUploadProgress,
PopInDeleteConfirm,
],
bootstrap: [
AppComponent
],
schemas: [
CUSTOM_ELEMENTS_SCHEMA,
NO_ERRORS_SCHEMA
]
})
export class AppModule { }

View File

@ -0,0 +1,2 @@
<!--<canvas width="200" height="250" style="border:1px solid #d3d3d3;" id="imageCanvas" #imageCanvas></canvas>-->
<img src="{{cover}}"/>

View File

@ -0,0 +1,5 @@
img {
max-height: 250px;
max-width: 200px;
}

View File

@ -0,0 +1,59 @@
/** @file
* @author Edouard DUPIN
* @copyright 2018, Edouard DUPIN, all right reserved
* @license PROPRIETARY (see license file)
*/
import { Injectable, Component, OnInit, Input } from '@angular/core';
import { ModelResponseHttp } from '../../service/http-wrapper';
import { DataService } from '../../service/data';
@Component({
selector: 'data-image',
templateUrl: './data-image.html',
styleUrls: [ './data-image.less' ]
})
@Injectable()
export class ElementDataImageComponent implements OnInit {
// input parameters
@Input() id:number = -1;
cover: string = '';
/*
imageCanvas:any;
@ViewChild('imageCanvas')
set mainDivEl(el: ElementRef) {
if(el !== null && el !== undefined) {
this.imageCanvas = el.nativeElement;
}
}
*/
constructor(private dataService: DataService) {
}
ngOnInit() {
this.cover = this.dataService.getCoverThumbnailUrl(this.id);
/*
let canvas = this.imageCanvas.nativeElement;
let ctx = canvas.getContext("2d");
console.log(`Request thumnail for ---> ${this.id}`);
this.dataService.getImageThumbnail(this.id)
.then((result:ModelResponseHttp) => {
console.log(`plop ---> ${result.status}`);
const response = result.data as Response;
response.blob().then((value:Blob) => {
let img = new Image();
img.onload = function() {
//ctx.drawImage(img, 0, 0)
}
let imageUrl = URL.createObjectURL(value);
console.log(`get new image url blob: ${imageUrl}`);
//img.src = imageUrl;
})
}).catch(()=>{
console.log("plop ---> ");
});
//img.src = "../../assets/aCRF-PRV111_CLN-001 v1.4-images/aCRF-PRV111_CLN-001 v1.4-blank_0.jpg";
//ctx.drawImage(img, 10, 10, 250, 250);
*/
}
}

View File

@ -0,0 +1,19 @@
<div class="imgContainer-small">
<div *ngIf="cover">
<!--<data-image id="{{cover}}"></data-image>-->
<img src="{{cover}}"/>
</div>
<div *ngIf="!cover" class="noImage">
</div>
</div>
<div class="season-small">
Season {{numberSeason}}
</div>
<div class="description-small" *ngIf="count > 1">
{{count}} Episodes
</div>
<div class="description-small" *ngIf="count == 1">
{{count}} Episode
</div>

View File

@ -0,0 +1,35 @@
.imgContainer-small {
text-align: center;
width: 100px;
margin: 4px 15px 4px 10px;
height: 100px;
img {
max-height: 100px;
max-width: 100px;
}
.noImage {
height: 95px;
width: 95px;
//box-shadow: 0px 2px 4px 0 rgba(0, 0, 0, 0.7);
border: solid 2px;
border-color: rgba(0, 0, 0, 0.7);
margin: auto;
}
float: left;
}
.title-small {
height: 50px;
//width: 100%;
font-size: 35px;
display:inline-block;
font-weight: bold;
}
.description-small {
height: 30px;
font-size: 16px;
overflow:hidden;
vertical-align: middle;
}

View File

@ -0,0 +1,62 @@
/** @file
* @author Edouard DUPIN
* @copyright 2018, Edouard DUPIN, all right reserved
* @license PROPRIETARY (see license file)
*/
import { Injectable, Component, OnInit, Input } from '@angular/core';
import { SeasonService } from '../../service/season';
@Component({
selector: 'app-element-season',
templateUrl: './element-season.html',
styleUrls: [ './element-season.less' ]
})
@Injectable()
export class ElementSeasonComponent implements OnInit {
// input parameters
@Input() idSeason:number = -1;
error:string = '';
numberSeason:number = -1;
count:number = 0;
cover:string = '';
covers:Array<string> = [];
description:string = '';
constructor(private seasonService: SeasonService) {
}
ngOnInit() {
let self = this;
console.log(`get season properties id: ${ this.idSeason}`);
this.seasonService.get(this.idSeason)
.then((response) => {
self.error = '';
self.numberSeason = response.name;
self.description = response.description;
if(response.covers === undefined || response.covers === null || response.covers.length === 0) {
self.cover = null;
// self.covers = [];
} else {
self.cover = response.covers[0];//self.seasonService.getCoverThumbnailUrl(response.covers[0]);
for(let iii = 0; iii < response.covers.length; iii++) {
self.covers.push(self.seasonService.getCoverThumbnailUrl(response.covers[iii]));
}
}
}).catch((response) => {
self.error = 'Can not get the data';
self.numberSeason = -1;
self.cover = null;
self.covers = [];
self.description = '';
});
this.seasonService.countVideo(this.idSeason)
.then((response) => {
self.count = response;
}).catch((response) => {
self.count = null;
});
}
}

View File

@ -0,0 +1,24 @@
<div>
<div class="count-base">
<div class="count" *ngIf="countvideo">
{{countvideo}}
</div>
</div>
<div class="imgContainer-small">
<div *ngIf="cover">
<!--<data-image id="{{cover}}"></data-image>-->
<img src="{{cover}}"/>
</div>
<div *ngIf="!cover" class="noImage">
</div>
</div>
<div class="title-small">
{{name}}
</div>
<!--
<div class="description-small" *ngIf="description">
{{description}}
</div>
-->
</div>

Some files were not shown because too many files have changed in this diff Show More