customeranalytics 0.1__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- customeranalytics/__init__.py +319 -0
- customeranalytics/configs.py +480 -0
- customeranalytics/data_storage_configurations/__init__.py +245 -0
- customeranalytics/data_storage_configurations/data_access.py +165 -0
- customeranalytics/data_storage_configurations/data_works_pipeline.py +207 -0
- customeranalytics/data_storage_configurations/es_create_index.py +544 -0
- customeranalytics/data_storage_configurations/logger.py +36 -0
- customeranalytics/data_storage_configurations/query_es.py +157 -0
- customeranalytics/data_storage_configurations/reports.py +684 -0
- customeranalytics/data_storage_configurations/schedule_data_integration.py +355 -0
- customeranalytics/docs/queries.yaml +245 -0
- customeranalytics/docs/web_configs.yaml +2 -0
- customeranalytics/exploratory_analysis/__init__.py +109 -0
- customeranalytics/exploratory_analysis/churn.py +232 -0
- customeranalytics/exploratory_analysis/cohorts.py +535 -0
- customeranalytics/exploratory_analysis/descriptive_statistics.py +470 -0
- customeranalytics/exploratory_analysis/funnels.py +407 -0
- customeranalytics/exploratory_analysis/product_analytics.py +340 -0
- customeranalytics/exploratory_analysis/promotion_analytics.py +299 -0
- customeranalytics/exploratory_analysis/rfm.py +202 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_avg_order_count_per_promo_per_cust.csv +99 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_chart_1_search.csv +2 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_chart_2_search.csv +46 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_chart_3_search.csv +2 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_chart_4_search.csv +2 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_churn.csv +2 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_churn_weekly.csv +10 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_client_feature_predicted.csv +1590 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_client_kpis.csv +7060 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_clvrfm_anomaly.csv +561 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_clvsegments_amount.csv +8 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_customer_journey.csv +18 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_clv.csv +103 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_cohort_downloads.csv +68 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_cohort_from_1_to_2.csv +66 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_cohort_from_2_to_3.csv +64 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_cohort_from_3_to_4.csv +55 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_dimension_values.csv +199 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_funnel.csv +36 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_funnel_downloads.csv +68 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_inorganic_ratio.csv +6070 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_orders.csv +57 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_organic_orders.csv +64 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_products_of_sales.csv +12574 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_promotion_discount.csv +64 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_daily_promotion_revenue.csv +6070 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_dcohort_anomaly.csv +6 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_dcohort_anomaly_2.csv +118 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_deliver.csv +47 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_deliver_kpis.csv +2 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_deliver_weekday_hour.csv +25 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_dfunnel_anomaly.csv +118 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_dimension_kpis.csv +199 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_dorders_anomaly.csv +85 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_frequency_clusters.csv +6 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_frequency_recency.csv +3740 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_hourly_funnel.csv +25 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_hourly_funnel_downloads.csv +25 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_hourly_inorganic_ratio.csv +2353 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_hourly_orders.csv +25 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_hourly_organic_orders.csv +2353 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_inorganic_orders_per_promotion_per_day.csv +6070 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_kpis.csv +2 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_monetary_clusters.csv +6 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_monetary_frequency.csv +3740 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_monthly_funnel.csv +5 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_monthly_funnel_downloads.csv +5 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_monthly_orders.csv +4 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_most_combined_products.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_most_ordered_categories.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_most_ordered_products.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_order_and_payment_amount_differences.csv +91 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_prepare.csv +101 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_prepare_weekday_hour.csv +25 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_product_kpis.csv +201 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_product_usage_before_after_amount_accept.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_product_usage_before_after_amount_reject.csv +7 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_product_usage_before_after_orders_accept.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_product_usage_before_after_orders_reject.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_promotion_comparison.csv +91 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_promotion_kpis.csv +99 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_promotion_number_of_customer.csv +99 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_promotion_usage_before_after_amount_accept.csv +81 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_promotion_usage_before_after_amount_reject.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_promotion_usage_before_after_orders_accept.csv +55 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_promotion_usage_before_after_orders_reject.csv +37 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_purchase_amount_distribution.csv +22 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_recency_clusters.csv +6 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_recency_monetary.csv +3740 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_rfm.csv +2001 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_ride.csv +101 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_ride_weekday_hour.csv +25 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_segmentation.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_segments_change_daily_before_after_amount.csv +10 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_segments_change_daily_before_after_orders.csv +9 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_segments_change_monthly_before_after_amount.csv +10 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_segments_change_monthly_before_after_orders.csv +11 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_segments_change_weekly_before_after_amount.csv +10 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_segments_change_weekly_before_after_orders.csv +10 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_user_counts_per_order_seq.csv +47 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_average_order_per_user.csv +13 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_average_payment_amount.csv +13 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_average_session_per_user.csv +13 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_cohort_downloads.csv +13 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_cohort_from_1_to_2.csv +13 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_cohort_from_2_to_3.csv +13 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_cohort_from_3_to_4.csv +12 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_funnel.csv +25 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_funnel_downloads.csv +25 -0
- customeranalytics/exploratory_analysis/sample_data/sample_data_weekly_orders.csv +10 -0
- customeranalytics/ml_process/__init__.py +64 -0
- customeranalytics/ml_process/ab_test.py +615 -0
- customeranalytics/ml_process/anomaly_detection.py +456 -0
- customeranalytics/ml_process/clv_prediction.py +301 -0
- customeranalytics/ml_process/customer_segmentation.py +354 -0
- customeranalytics/ml_process/delivery_analytics.py +754 -0
- customeranalytics/utils.py +186 -0
- customeranalytics/web/app/__init__.py +37 -0
- customeranalytics/web/app/base/__init__.py +9 -0
- customeranalytics/web/app/base/forms.py +16 -0
- customeranalytics/web/app/base/models.py +43 -0
- customeranalytics/web/app/base/routes.py +126 -0
- customeranalytics/web/app/base/static/assets/css/app.css +20 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Black.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Black.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-BlackItalic.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-BlackItalic.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Bold.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Bold.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-BoldItalic.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-BoldItalic.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ExtraBold.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ExtraBold.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ExtraBoldItalic.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ExtraBoldItalic.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ExtraLight-BETA.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ExtraLight-BETA.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ExtraLightItalic-BETA.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ExtraLightItalic-BETA.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Italic.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Italic.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Light-BETA.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Light-BETA.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-LightItalic-BETA.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-LightItalic-BETA.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Medium.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Medium.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-MediumItalic.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-MediumItalic.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Regular.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Regular.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-SemiBold.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-SemiBold.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-SemiBoldItalic.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-SemiBoldItalic.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Thin-BETA.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-Thin-BETA.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ThinItalic-BETA.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-ThinItalic-BETA.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-italic.var.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter-upright.var.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/Inter.var.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-brands-400.eot +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-brands-400.svg +3570 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-brands-400.ttf +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-brands-400.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-brands-400.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-regular-400.eot +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-regular-400.svg +801 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-regular-400.ttf +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-regular-400.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-regular-400.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-solid-900.eot +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-solid-900.svg +5028 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-solid-900.ttf +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-solid-900.woff +0 -0
- customeranalytics/web/app/base/static/assets/fonts/fa-solid-900.woff2 +0 -0
- customeranalytics/web/app/base/static/assets/img/avatars/avatar-1.png +0 -0
- customeranalytics/web/app/base/static/assets/img/avatars/avatar-2.png +0 -0
- customeranalytics/web/app/base/static/assets/img/avatars/avatar-3.png +0 -0
- customeranalytics/web/app/base/static/assets/img/avatars/avatar-4.png +0 -0
- customeranalytics/web/app/base/static/assets/img/avatars/avatar-5.png +0 -0
- customeranalytics/web/app/base/static/assets/img/avatars/info.jpeg +0 -0
- customeranalytics/web/app/base/static/assets/img/icons/customanality.png +0 -0
- customeranalytics/web/app/base/static/assets/img/icons/icon-48x48.png +0 -0
- customeranalytics/web/app/base/static/assets/js/app.js +2 -0
- customeranalytics/web/app/base/static/assets/js/app.js.LICENSE +566 -0
- customeranalytics/web/app/base/static/assets/js/app.js.LICENSE.txt +556 -0
- customeranalytics/web/app/base/static/assets/js/modules/bootstrap.js +15 -0
- customeranalytics/web/app/base/static/assets/js/modules/chartjs.js +4 -0
- customeranalytics/web/app/base/static/assets/js/modules/feather.js +8 -0
- customeranalytics/web/app/base/static/assets/js/modules/flatpickr.js +4 -0
- customeranalytics/web/app/base/static/assets/js/modules/moment.js +4 -0
- customeranalytics/web/app/base/static/assets/js/modules/sidebar.js +23 -0
- customeranalytics/web/app/base/static/assets/js/modules/theme.js +16 -0
- customeranalytics/web/app/base/templates/accounts/login.html +81 -0
- customeranalytics/web/app/base/templates/accounts/register.html +80 -0
- customeranalytics/web/app/base/templates/includes/footer.html +28 -0
- customeranalytics/web/app/base/templates/includes/navigation.html +51 -0
- customeranalytics/web/app/base/templates/includes/scripts.html +3 -0
- customeranalytics/web/app/base/templates/includes/sidebar.html +146 -0
- customeranalytics/web/app/base/templates/layouts/base-fullscreen.html +36 -0
- customeranalytics/web/app/base/templates/layouts/base.html +84 -0
- customeranalytics/web/app/base/util.py +30 -0
- customeranalytics/web/app/home/__init__.py +9 -0
- customeranalytics/web/app/home/forms.py +1039 -0
- customeranalytics/web/app/home/models.py +438 -0
- customeranalytics/web/app/home/profiles.py +310 -0
- customeranalytics/web/app/home/routes.py +386 -0
- customeranalytics/web/app/home/search.py +288 -0
- customeranalytics/web/app/home/static/assets/img/avatars/avatar-1.png +0 -0
- customeranalytics/web/app/home/static/assets/img/avatars/avatar-2.png +0 -0
- customeranalytics/web/app/home/static/assets/img/avatars/avatar-3.png +0 -0
- customeranalytics/web/app/home/static/assets/img/avatars/avatar-4.png +0 -0
- customeranalytics/web/app/home/static/assets/img/avatars/avatar-5.png +0 -0
- customeranalytics/web/app/home/static/assets/img/icons/customanality.png +0 -0
- customeranalytics/web/app/home/static/assets/img/icons/icon-48x48.png +0 -0
- customeranalytics/web/app/home/templates/abtest-product.html +280 -0
- customeranalytics/web/app/home/templates/abtest-promotion.html +362 -0
- customeranalytics/web/app/home/templates/abtest-segments.html +298 -0
- customeranalytics/web/app/home/templates/add-data-delivery.html +184 -0
- customeranalytics/web/app/home/templates/add-data-product.html +177 -0
- customeranalytics/web/app/home/templates/add-data-purchase.html +392 -0
- customeranalytics/web/app/home/templates/anomaly.html +261 -0
- customeranalytics/web/app/home/templates/clv.html +211 -0
- customeranalytics/web/app/home/templates/cohorts.html +308 -0
- customeranalytics/web/app/home/templates/customer-segmentation.html +308 -0
- customeranalytics/web/app/home/templates/data-es.html +152 -0
- customeranalytics/web/app/home/templates/data-execute.html +397 -0
- customeranalytics/web/app/home/templates/delivery.html +404 -0
- customeranalytics/web/app/home/templates/funnel-customer.html +240 -0
- customeranalytics/web/app/home/templates/funnel-session.html +236 -0
- customeranalytics/web/app/home/templates/index.html +524 -0
- customeranalytics/web/app/home/templates/index2.html +515 -0
- customeranalytics/web/app/home/templates/page-403.html +46 -0
- customeranalytics/web/app/home/templates/page-404.html +45 -0
- customeranalytics/web/app/home/templates/page-500.html +45 -0
- customeranalytics/web/app/home/templates/pages-blank.html +33 -0
- customeranalytics/web/app/home/templates/pages-sign-in.html +67 -0
- customeranalytics/web/app/home/templates/pages-sign-up.html +61 -0
- customeranalytics/web/app/home/templates/product.html +203 -0
- customeranalytics/web/app/home/templates/profile.html +1009 -0
- customeranalytics/web/app/home/templates/rfm.html +254 -0
- customeranalytics/web/app/home/templates/search.html +167 -0
- customeranalytics/web/app/home/templates/settings.html +205 -0
- customeranalytics/web/app/home/templates/stats-desc.html +230 -0
- customeranalytics/web/app/home/templates/stats-purchase.html +221 -0
- customeranalytics/web/config.py +30 -0
- customeranalytics/web/db.sqlite3 +0 -0
- customeranalytics/web/run.py +30 -0
- customeranalytics-0.1.dist-info/METADATA +1102 -0
- customeranalytics-0.1.dist-info/RECORD +254 -0
- customeranalytics-0.1.dist-info/WHEEL +4 -0
- customeranalytics-0.1.dist-info/licenses/LICENSE +21 -0
|
@@ -0,0 +1,544 @@
|
|
|
1
|
+
import sys, os, inspect
|
|
2
|
+
currentdir = os.path.dirname(os.path.abspath(inspect.getfile(inspect.currentframe())))
|
|
3
|
+
parentdir = os.path.dirname(currentdir)
|
|
4
|
+
sys.path.insert(0, parentdir)
|
|
5
|
+
import numpy as np
|
|
6
|
+
import pandas as pd
|
|
7
|
+
import datetime
|
|
8
|
+
import random
|
|
9
|
+
from time import gmtime, strftime
|
|
10
|
+
import pytz
|
|
11
|
+
from elasticsearch import Elasticsearch
|
|
12
|
+
from elasticsearch import helpers
|
|
13
|
+
import argparse
|
|
14
|
+
from dateutil.parser import parse
|
|
15
|
+
from sqlalchemy import create_engine, MetaData
|
|
16
|
+
from flask_login import current_user
|
|
17
|
+
from os.path import abspath, join
|
|
18
|
+
import time
|
|
19
|
+
|
|
20
|
+
from customeranalytics.utils import read_yaml, current_date_to_day, convert_to_date, convert_to_iso_format, formating_numbers
|
|
21
|
+
from customeranalytics.configs import query_path, default_es_port, default_es_host, none_types, delivery_metrics
|
|
22
|
+
from customeranalytics.configs import orders_index_columns, downloads_index_columns, not_required_columns, not_required_default_values
|
|
23
|
+
from customeranalytics.data_storage_configurations.query_es import QueryES
|
|
24
|
+
from customeranalytics.data_storage_configurations.data_access import GetData
|
|
25
|
+
|
|
26
|
+
try:
|
|
27
|
+
engine = create_engine('sqlite://///' + join(abspath(""), "web", 'db.sqlite3'), connect_args={'check_same_thread': False})
|
|
28
|
+
metadata = MetaData()
|
|
29
|
+
con = engine.connect()
|
|
30
|
+
except Exception as e:
|
|
31
|
+
engine = create_engine('sqlite://///' + join(parentdir, "web", 'db.sqlite3'), connect_args={'check_same_thread': False})
|
|
32
|
+
metadata = MetaData()
|
|
33
|
+
con = engine.connect()
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
class CreateIndex:
|
|
37
|
+
"""
|
|
38
|
+
This class is converting input data to elasticsearch index.
|
|
39
|
+
This allow us to query data from elasticsearch.
|
|
40
|
+
Each business has on its own way to store data.
|
|
41
|
+
This is a generic way to store the data into the elasticsearch indexes
|
|
42
|
+
"""
|
|
43
|
+
def __init__(self, data_connection_structure, data_columns, actions):
|
|
44
|
+
"""
|
|
45
|
+
data_sets:
|
|
46
|
+
* orders:
|
|
47
|
+
each purchased orders row by row
|
|
48
|
+
columns: order_id, client, start_date, purchase_date, purchase_amount, discount_amount
|
|
49
|
+
optional columns: purchase_date, discount_amount
|
|
50
|
+
* products:
|
|
51
|
+
****** OPTIONAL DATA *******
|
|
52
|
+
each purchased orders of products row by row.
|
|
53
|
+
columns: order_id, product_id, product_category, product_price, rank
|
|
54
|
+
optional columns: product_category, product_price, rank
|
|
55
|
+
* promos:
|
|
56
|
+
****** OPTIONAL DATA *******
|
|
57
|
+
each order of promotion status
|
|
58
|
+
please assign only if there is discount at order
|
|
59
|
+
columns: order_id, promotion_id
|
|
60
|
+
* sessions:
|
|
61
|
+
columns: session_id, client_id
|
|
62
|
+
* actions:
|
|
63
|
+
****** OPTIONAL DATA *******
|
|
64
|
+
columns: session_id, client_id, action_1 (boolean: True/False), .. action_10 (boolean: True/False)
|
|
65
|
+
* action_details:
|
|
66
|
+
****** OPTIONAL DATA *******
|
|
67
|
+
detail of action
|
|
68
|
+
columns: session_id, action_name (action_1, action_2, ..., action_10), detail_1, detail_2, detail_3
|
|
69
|
+
|
|
70
|
+
|
|
71
|
+
indicator columns:
|
|
72
|
+
These are type of indicator columns;
|
|
73
|
+
e.g.
|
|
74
|
+
:param data_connection_structure: data connections
|
|
75
|
+
:param data_columns: matched columns
|
|
76
|
+
"""
|
|
77
|
+
self.data_connection_structure = data_connection_structure
|
|
78
|
+
self.data_columns = data_columns
|
|
79
|
+
self.actions = actions
|
|
80
|
+
self.sqlite_queries = read_yaml(query_path, "queries.yaml")
|
|
81
|
+
self.tables = pd.read_sql(self.sqlite_queries['tables'], con)
|
|
82
|
+
self.query_es = QueryES()
|
|
83
|
+
self.es_cons = pd.DataFrame()
|
|
84
|
+
self.schedule = pd.DataFrame()
|
|
85
|
+
self.start_date, self.end_date = None, None
|
|
86
|
+
self.ebd_date = current_date_to_day()
|
|
87
|
+
self.port = default_es_port
|
|
88
|
+
self.host = default_es_host
|
|
89
|
+
self.latest_session_transaction_date = None
|
|
90
|
+
self.result_data = pd.DataFrame()
|
|
91
|
+
self.job_start_date = None
|
|
92
|
+
self.info_logs_for_chat = lambda info: {'user': 'info',
|
|
93
|
+
'date': str(current_date_to_day())[0:19],
|
|
94
|
+
'user_logo': 'info.jpeg',
|
|
95
|
+
'chat_type': 'info', 'chart': '',
|
|
96
|
+
'general_message': info, 'message': ''}
|
|
97
|
+
|
|
98
|
+
def insert_query(self, table, columns, values):
|
|
99
|
+
values = [values[col] for col in columns]
|
|
100
|
+
_query = "INSERT INTO " + table + " "
|
|
101
|
+
_query += " (" + ", ".join(columns) + ") "
|
|
102
|
+
_query += " VALUES (" + ", ".join([" '{}' ".format(v) for v in values]) + ") "
|
|
103
|
+
_query = _query.replace("\\", "")
|
|
104
|
+
return _query
|
|
105
|
+
|
|
106
|
+
def update_query(self, table, condition, columns, values):
|
|
107
|
+
values = [(col, values[col]) for col in columns if values.get(col, None) is not None]
|
|
108
|
+
_query = "UPDATE " + table
|
|
109
|
+
_query += " SET " + ", ".join([i[0] + " = '" + i[1] + "'" for i in values])
|
|
110
|
+
_query +=" WHERE " + condition
|
|
111
|
+
_query = _query.replace("\\", "")
|
|
112
|
+
return _query
|
|
113
|
+
|
|
114
|
+
def check_for_table_exits(self, table, query=None):
|
|
115
|
+
try:
|
|
116
|
+
if table not in list(self.tables['name']):
|
|
117
|
+
if query is None:
|
|
118
|
+
con.execute(self.sqlite_queries[table])
|
|
119
|
+
else:
|
|
120
|
+
con.execute(query)
|
|
121
|
+
except Exception as e:
|
|
122
|
+
print(e)
|
|
123
|
+
|
|
124
|
+
def logs_update(self, logs):
|
|
125
|
+
"""
|
|
126
|
+
logs table in sqlite table is updated.
|
|
127
|
+
chats table in sqlite table is updated.
|
|
128
|
+
"""
|
|
129
|
+
try: self.check_for_table_exits(table='logs')
|
|
130
|
+
except Exception as e: print(e)
|
|
131
|
+
|
|
132
|
+
try: self.check_for_table_exits(table='chat')
|
|
133
|
+
except Exception as e: print(e)
|
|
134
|
+
|
|
135
|
+
try:
|
|
136
|
+
logs['login_user'] = current_user
|
|
137
|
+
logs['log_time'] = str(current_date_to_day())[0:19]
|
|
138
|
+
logs['general_message'] = logs['info']
|
|
139
|
+
con.execute(self.insert_query(table='logs',
|
|
140
|
+
columns=self.sqlite_queries['columns']['logs'][1:],
|
|
141
|
+
values=logs
|
|
142
|
+
))
|
|
143
|
+
except Exception as e:
|
|
144
|
+
print(e)
|
|
145
|
+
|
|
146
|
+
try: con.execute(self.insert_query(table='chat', columns=self.sqlite_queries['columns']['chat'][1:],
|
|
147
|
+
values=self.info_logs_for_chat(logs['info'])))
|
|
148
|
+
except Exception as e: print(e)
|
|
149
|
+
|
|
150
|
+
def update_schedule(self, date):
|
|
151
|
+
self.check_for_table_exits(table='schedule_data')
|
|
152
|
+
try:
|
|
153
|
+
con.execute(self.update_query(table='schedule_data',
|
|
154
|
+
condition=" id = 1",
|
|
155
|
+
columns=['max_date_of_order_data'],
|
|
156
|
+
values= {'max_date_of_order_data': date}
|
|
157
|
+
))
|
|
158
|
+
except Exception as e:
|
|
159
|
+
print(e)
|
|
160
|
+
|
|
161
|
+
def collect_es_connection_infos(self):
|
|
162
|
+
self.es_cons = pd.read_sql("SELECT * FROM es_connection", con)
|
|
163
|
+
self.port = list(self.es_cons['port'])[0]
|
|
164
|
+
self.host = list(self.es_cons['host'])[0]
|
|
165
|
+
|
|
166
|
+
def create_index_connection(self):
|
|
167
|
+
self.collect_es_connection_infos()
|
|
168
|
+
self.query_es = QueryES(port=self.port, host=self.host)
|
|
169
|
+
|
|
170
|
+
def index_count(self, index):
|
|
171
|
+
_count = int(self.query_es.es.cat.count(index, params={"format": "json"})[0]['count'])
|
|
172
|
+
return _count
|
|
173
|
+
|
|
174
|
+
def check_and_create_index(self, index):
|
|
175
|
+
self.create_index_connection()
|
|
176
|
+
accept = False if self.query_es.check_index_exists(index=index) is None else True
|
|
177
|
+
if accept:
|
|
178
|
+
if self.index_count(index) != 0:
|
|
179
|
+
accept = True
|
|
180
|
+
return accept
|
|
181
|
+
|
|
182
|
+
def get_schedule_data(self):
|
|
183
|
+
self.schedule = pd.read_sql("SELECT * FROM schedule_data", con)
|
|
184
|
+
|
|
185
|
+
def get_start_date(self):
|
|
186
|
+
if list(self.schedule['time_period'])[0] != 'once':
|
|
187
|
+
self.start_date = convert_to_date(list(self.schedule['max_date_of_order_data'])[0])
|
|
188
|
+
|
|
189
|
+
def get_end_date(self):
|
|
190
|
+
if list(self.schedule['time_period'])[0] != 'once':
|
|
191
|
+
self.end_date = current_date_to_day()
|
|
192
|
+
|
|
193
|
+
def design_order_basket(self, x):
|
|
194
|
+
try:
|
|
195
|
+
result = {}
|
|
196
|
+
for i in x:
|
|
197
|
+
for p in list(i.keys()):
|
|
198
|
+
result[p] = i[p]
|
|
199
|
+
return result
|
|
200
|
+
except Exception as e:
|
|
201
|
+
print(e)
|
|
202
|
+
return None
|
|
203
|
+
|
|
204
|
+
def change_columns_format(self, data, data_source_type):
|
|
205
|
+
columns = list(data.columns)
|
|
206
|
+
if data_source_type in ['orders', 'products', 'deliveries']:
|
|
207
|
+
data['order_id'] = data['order_id'].apply(lambda x: str(x))
|
|
208
|
+
if data_source_type in ['orders', 'downloads']:
|
|
209
|
+
data['client'] = data['client'].apply(lambda x: str(x))
|
|
210
|
+
if data_source_type == 'orders':
|
|
211
|
+
data['session_start_date'] = data['session_start_date'].apply(lambda x: parse(x))
|
|
212
|
+
data['payment_amount'] = data['payment_amount'].apply(
|
|
213
|
+
lambda x: float(x) if x == x and x not in ['None', None, 'nan'] else None)
|
|
214
|
+
if 'discount_amount' in columns:
|
|
215
|
+
data['discount_amount'] = data['discount_amount'].apply(
|
|
216
|
+
lambda x: float(x) if x == x and x not in ['None', None, 'nan'] else None)
|
|
217
|
+
if 'date' in columns:
|
|
218
|
+
data['date'] = data['date'].apply(
|
|
219
|
+
lambda x: parse(x) if x == x and x not in ['None', None, 'nan'] else None)
|
|
220
|
+
if 'promotion_id' in columns:
|
|
221
|
+
data['promotion_id'] = data['promotion_id'].apply(
|
|
222
|
+
lambda x: x if x == x and x not in ['None', None, 'nan'] else None)
|
|
223
|
+
if data_source_type == 'deliveries':
|
|
224
|
+
for col in delivery_metrics:
|
|
225
|
+
if col in columns:
|
|
226
|
+
data[col] = data[col].apply(
|
|
227
|
+
lambda x: parse(x) if col in ['return_date', 'prepare_date', 'delivery_date'] else float(x))
|
|
228
|
+
if data_source_type == 'downloads':
|
|
229
|
+
data['download_date'] = data['download_date'].apply(
|
|
230
|
+
lambda x: parse(x) if x == x and x not in ['None', None, 'nan'] else None)
|
|
231
|
+
if 'signup_date' in columns:
|
|
232
|
+
data['signup_date'] = data['signup_date'].apply(
|
|
233
|
+
lambda x: parse(x) if x == x and x not in ['None', None, 'nan'] else None)
|
|
234
|
+
if data_source_type == 'products':
|
|
235
|
+
if 'price' in columns:
|
|
236
|
+
data['price'] = data['price'].apply(
|
|
237
|
+
lambda x: float(x) if x == x and x not in ['None', None, 'nan'] else None)
|
|
238
|
+
return data
|
|
239
|
+
|
|
240
|
+
def get_index_of_last_date(self, date_column, index):
|
|
241
|
+
try:
|
|
242
|
+
match = {"size": 1, "from": 0, "_source": True, "sort": {date_column: "desc"}, }
|
|
243
|
+
res = self.query_es.es.search(index=index, body=match)['hits']['hits']
|
|
244
|
+
return convert_to_date([r['_source'][date_column] for r in res][0])
|
|
245
|
+
except Exception as e:
|
|
246
|
+
print("session_start_date/download_date is not inserted into the indexes.")
|
|
247
|
+
return None
|
|
248
|
+
|
|
249
|
+
def collect_prev_downloads(self):
|
|
250
|
+
try:
|
|
251
|
+
match = {"size": 100000, "from": 0, "_source": True}
|
|
252
|
+
res = self.query_es.es.search(index='downloads', body=match)['hits']['hits']
|
|
253
|
+
return [r['_source']['client'] for r in res]
|
|
254
|
+
except Exception as e:
|
|
255
|
+
print(e)
|
|
256
|
+
return []
|
|
257
|
+
|
|
258
|
+
def filter_dates(self, data, data_source_type):
|
|
259
|
+
"""
|
|
260
|
+
|
|
261
|
+
"""
|
|
262
|
+
try:
|
|
263
|
+
if data_source_type in ['orders', 'downloads']:
|
|
264
|
+
date_column = "session_start_date" if data_source_type == 'orders' else "download_date"
|
|
265
|
+
max_index_date = self.get_index_of_last_date(date_column, data_source_type)
|
|
266
|
+
if self.start_date is not None:
|
|
267
|
+
data = data[data[date_column] >= self.start_date]
|
|
268
|
+
if self.end_date is not None:
|
|
269
|
+
data = data[data[date_column] < self.end_date]
|
|
270
|
+
if max_index_date is not None:
|
|
271
|
+
data = data[data[date_column] >= max_index_date]
|
|
272
|
+
if data_source_type == 'downloads':
|
|
273
|
+
data[~data['client'].isin(self.collect_prev_downloads())]
|
|
274
|
+
except Exception as e:
|
|
275
|
+
print(e)
|
|
276
|
+
return data
|
|
277
|
+
|
|
278
|
+
def check_columns(self, col):
|
|
279
|
+
_col = col
|
|
280
|
+
if col == 'client_2':
|
|
281
|
+
_col = 'client'
|
|
282
|
+
if col == 'order_id_2':
|
|
283
|
+
_col = 'order_id'
|
|
284
|
+
return _col
|
|
285
|
+
|
|
286
|
+
def match_data_columns(self, data):
|
|
287
|
+
cols = list(data.columns)
|
|
288
|
+
renaming = {}
|
|
289
|
+
for col in self.data_columns:
|
|
290
|
+
if self.data_columns[col] in cols:
|
|
291
|
+
renaming[self.data_columns[col]] = self.check_columns(col)
|
|
292
|
+
return data.rename(columns=renaming)
|
|
293
|
+
|
|
294
|
+
def check_for_not_required_columns(self, data, data_source_type):
|
|
295
|
+
_columns = list(data.columns)
|
|
296
|
+
for col in not_required_columns[data_source_type]:
|
|
297
|
+
if col not in _columns:
|
|
298
|
+
data[col] = not_required_default_values[col]
|
|
299
|
+
return data
|
|
300
|
+
|
|
301
|
+
def get_data(self, conf, data_source_type):
|
|
302
|
+
"""
|
|
303
|
+
{'data_source': connection[index + '_data_source_type'],
|
|
304
|
+
'date': date,
|
|
305
|
+
'data_query_path': connection[index + '_data_query_path'],
|
|
306
|
+
'test': test,
|
|
307
|
+
'config': {'host': connection[index + '_host'],
|
|
308
|
+
'port': connection[index + '_port'],
|
|
309
|
+
'password': connection[index + '_password'],
|
|
310
|
+
'user': connection[index + '_user'], 'db': connection[index + '_db']}
|
|
311
|
+
}
|
|
312
|
+
"""
|
|
313
|
+
gd = GetData(data_source=conf['data_source'],
|
|
314
|
+
data_query_path=conf['data_query_path'], config=conf['config'], test=1000)
|
|
315
|
+
gd.query_data_source()
|
|
316
|
+
gd = GetData(data_source=conf['data_source'],
|
|
317
|
+
data_query_path=conf['data_query_path'], config=conf['config'])
|
|
318
|
+
gd.query_data_source()
|
|
319
|
+
data = self.match_data_columns(data=gd.data)
|
|
320
|
+
data = self.change_columns_format(data, data_source_type)
|
|
321
|
+
data = self.filter_dates(data, data_source_type)
|
|
322
|
+
data = self.check_for_not_required_columns(data, data_source_type)
|
|
323
|
+
return data
|
|
324
|
+
|
|
325
|
+
def merge_orders(self, order_source, product_source, delivery_source):
|
|
326
|
+
orders = pd.DataFrame()
|
|
327
|
+
try:
|
|
328
|
+
orders = self.get_data(conf=order_source, data_source_type='orders')
|
|
329
|
+
except Exception as e:
|
|
330
|
+
print(e)
|
|
331
|
+
|
|
332
|
+
if len(orders) != 0:
|
|
333
|
+
try:
|
|
334
|
+
if product_source.get('data_query_path', None) is not None:
|
|
335
|
+
products = self.get_data(conf=product_source, data_source_type='products')
|
|
336
|
+
products['basket'] = products.apply(
|
|
337
|
+
lambda row: {row['product']: {'price': row['price'],
|
|
338
|
+
'category': row['category']}}, axis=1)
|
|
339
|
+
products = products.groupby("order_id").agg({"basket":
|
|
340
|
+
lambda x: self.design_order_basket(x)}).reset_index()
|
|
341
|
+
products['total_products'] = products['basket'].apply(lambda x: len(x.keys()))
|
|
342
|
+
orders = pd.merge(orders, products, on='order_id', how='left')
|
|
343
|
+
orders['basket'] = orders['basket'].fillna({})
|
|
344
|
+
del products
|
|
345
|
+
else: orders['basket'] = None
|
|
346
|
+
except Exception as e:
|
|
347
|
+
print(e)
|
|
348
|
+
orders['basket'] = None
|
|
349
|
+
|
|
350
|
+
try:
|
|
351
|
+
if delivery_source.get('data_query_path', None) is not None:
|
|
352
|
+
deliveries = self.get_data(conf=delivery_source, data_source_type='deliveries')
|
|
353
|
+
deliveries = deliveries.groupby("order_id").agg({m: 'first' for m in delivery_metrics}).reset_index()
|
|
354
|
+
deliveries['delivery'] = deliveries.apply(lambda row: {m: row[m] for m in delivery_metrics}, axis=1)
|
|
355
|
+
orders = pd.merge(orders, deliveries[['order_id', 'delivery']], on='order_id', how='left')
|
|
356
|
+
else: orders['delivery'] = None
|
|
357
|
+
except Exception as e:
|
|
358
|
+
print(e)
|
|
359
|
+
orders['delivery'] = None
|
|
360
|
+
|
|
361
|
+
return orders
|
|
362
|
+
|
|
363
|
+
def partial_insert(self, _insert, index):
|
|
364
|
+
counter = 0
|
|
365
|
+
while counter < 10:
|
|
366
|
+
try:
|
|
367
|
+
self.query_es.insert_data_to_index(_insert, index)
|
|
368
|
+
counter = 10
|
|
369
|
+
except Exception as e:
|
|
370
|
+
print(e)
|
|
371
|
+
counter += 1
|
|
372
|
+
|
|
373
|
+
def insert_to_index(self, data, index):
|
|
374
|
+
"""
|
|
375
|
+
Sessions (Orders) Index Document;
|
|
376
|
+
{'_index': 'orders',
|
|
377
|
+
'_type': '_doc',
|
|
378
|
+
'_id': 'VgxgE3cBdDDj70WtOuFJ',
|
|
379
|
+
'_score': 1.0,
|
|
380
|
+
'_source': {'id': 74915741,
|
|
381
|
+
'date': '2020-12-16T09:47:00',
|
|
382
|
+
'actions': {'has_sessions': True,
|
|
383
|
+
'has_basket': True,
|
|
384
|
+
'order_screen': True,
|
|
385
|
+
'purchased': False},
|
|
386
|
+
'client': 'u_382139',
|
|
387
|
+
'dimension': 'location_1',
|
|
388
|
+
'promotion_id': None,
|
|
389
|
+
'payment_amount': 52.75500000000001,
|
|
390
|
+
'discount_amount': 0,
|
|
391
|
+
'basket': {'p_10': {'price': 6.12, 'category': 'p_c_8', 'rank': 109},....},
|
|
392
|
+
'delivery': {'delivery_date': '2020-12-16T09:39:11',
|
|
393
|
+
'return_date': '2020-12-16T09:39:11',
|
|
394
|
+
'prepare_date': '2020-12-16T09:39:11',
|
|
395
|
+
'latitude':43,2342131232, 'longitude': 34,2342131232}
|
|
396
|
+
'total_products': 7,
|
|
397
|
+
'session_start_date': '2020-12-16T09:39:11'}}
|
|
398
|
+
|
|
399
|
+
Customers (Downloads) Index Document;
|
|
400
|
+
{'id': 3840375,
|
|
401
|
+
'download_date': '2020-12-31T14:56:32',
|
|
402
|
+
'signup_date': '2021-01-02T13:55:32', 'client': 'u_344313'}
|
|
403
|
+
"""
|
|
404
|
+
try:
|
|
405
|
+
_insert = []
|
|
406
|
+
data = data.to_dict('records')
|
|
407
|
+
if index == 'orders':
|
|
408
|
+
for i in data:
|
|
409
|
+
_obj = {i: None for i in orders_index_columns}
|
|
410
|
+
_keys = list(i.keys())
|
|
411
|
+
_has_purchased = True if i['has_purchased'] in ['True', True] else False
|
|
412
|
+
if len(self.actions[index]) != 0:
|
|
413
|
+
_obj['actions'] = {_a: False for _a in self.actions[index]}
|
|
414
|
+
_obj['actions']['purchased'] = _has_purchased
|
|
415
|
+
_obj['actions']['has_sessions'] = True
|
|
416
|
+
else:
|
|
417
|
+
_obj['actions'] = {'purchased': _has_purchased, 'has_sessions': True}
|
|
418
|
+
|
|
419
|
+
if i['delivery'] is not None:
|
|
420
|
+
_delivery = {}
|
|
421
|
+
if i['delivery'] == i['delivery']:
|
|
422
|
+
_delivery = i['delivery']
|
|
423
|
+
try:
|
|
424
|
+
for k in ['return_date', 'prepare_date', 'delivery_date']:
|
|
425
|
+
if _delivery[k] not in ['None', None, 'nan']:
|
|
426
|
+
_delivery[k] = convert_to_iso_format(i['delivery'][k])
|
|
427
|
+
else:
|
|
428
|
+
_delivery[k] = convert_to_iso_format(i['session_start_date'])
|
|
429
|
+
except Exception as e:
|
|
430
|
+
print(e)
|
|
431
|
+
i['delivery'] = _delivery
|
|
432
|
+
|
|
433
|
+
for k in _obj:
|
|
434
|
+
if k in _keys:
|
|
435
|
+
if k in ['date', 'session_start_date']:
|
|
436
|
+
_obj[k] = convert_to_iso_format(i[k])
|
|
437
|
+
else:
|
|
438
|
+
_obj[k] = i[k] if i[k] == i[k] and i[k] not in ['None', None, 'nan'] else None
|
|
439
|
+
else:
|
|
440
|
+
if k == 'id':
|
|
441
|
+
_obj['id'] = i['order_id']
|
|
442
|
+
if k == 'basket':
|
|
443
|
+
_obj['basket'] = i['basket'] if i['basket'] == i['basket'] else {}
|
|
444
|
+
if k == 'actions':
|
|
445
|
+
for a in self.actions[index]:
|
|
446
|
+
if a in _keys:
|
|
447
|
+
if i[a]:
|
|
448
|
+
_obj['actions'][a] = True
|
|
449
|
+
_insert.append(_obj)
|
|
450
|
+
del _obj
|
|
451
|
+
if len(_insert) >= 10:
|
|
452
|
+
self.partial_insert(_insert, index)
|
|
453
|
+
_insert = []
|
|
454
|
+
|
|
455
|
+
if len(_insert) != 0:
|
|
456
|
+
self.partial_insert(_insert, index)
|
|
457
|
+
# insert logs into the sqlite logs table for sessions data insert process
|
|
458
|
+
self.logs_update(logs={"page": "data-execute",
|
|
459
|
+
"info": " SESSIONS index Done! - Number of documents :" + formating_numbers(len(data)),
|
|
460
|
+
"color": "green"})
|
|
461
|
+
_insert = []
|
|
462
|
+
if index == 'downloads':
|
|
463
|
+
for i in data:
|
|
464
|
+
_keys = list(i.keys())
|
|
465
|
+
_obj = {i: None for i in downloads_index_columns}
|
|
466
|
+
# TODO : id must be the counter not randomly selected
|
|
467
|
+
_obj['id'] = np.random.randint(200000000)
|
|
468
|
+
_obj['client'] = i['client']
|
|
469
|
+
_obj['download_date'] = convert_to_iso_format(i['download_date'])
|
|
470
|
+
if i.get('signup_date', None) is not None:
|
|
471
|
+
if i['signup_date'] not in ['nan', None, '', '-', 'Null']:
|
|
472
|
+
try:
|
|
473
|
+
_obj['signup_date'] = convert_to_iso_format(i['signup_date'])
|
|
474
|
+
except Exception as e_signup:
|
|
475
|
+
_obj['signup_date'] = None
|
|
476
|
+
|
|
477
|
+
for _a in self.actions[index]:
|
|
478
|
+
if i[_a] == i[_a]:
|
|
479
|
+
_obj[_a] = convert_to_iso_format(i[_a])
|
|
480
|
+
|
|
481
|
+
_insert.append(_obj)
|
|
482
|
+
if len(_insert) >= 10:
|
|
483
|
+
self.partial_insert(_insert, index)
|
|
484
|
+
_insert = []
|
|
485
|
+
|
|
486
|
+
if len(_insert) != 0:
|
|
487
|
+
self.partial_insert(_insert, index)
|
|
488
|
+
# insert logs into the sqlite logs table for customers data insert process
|
|
489
|
+
self.logs_update(logs={"page": "data-execute",
|
|
490
|
+
"info": " CUSTOMERS index Done! - Number of documents :" + formating_numbers(len(data)),
|
|
491
|
+
"color": "green"})
|
|
492
|
+
|
|
493
|
+
except Exception as e:
|
|
494
|
+
try:
|
|
495
|
+
err_str = " - " + str(e).replace("'", " ")
|
|
496
|
+
err_str = err_str[0:100] if len(err_str) >= 100 else err_str
|
|
497
|
+
except: err_str = " "
|
|
498
|
+
self.logs_update(logs={"page": "data-execute",
|
|
499
|
+
"info": "indexes Creation is failed! While " + index + " is creating. " + err_str,
|
|
500
|
+
"color": "red"})
|
|
501
|
+
|
|
502
|
+
def execute_index(self):
|
|
503
|
+
"""
|
|
504
|
+
|
|
505
|
+
"""
|
|
506
|
+
self.job_start_date = current_date_to_day()
|
|
507
|
+
self.get_schedule_data()
|
|
508
|
+
self.get_end_date()
|
|
509
|
+
|
|
510
|
+
try:
|
|
511
|
+
for _data_type in ['orders', 'downloads']:
|
|
512
|
+
if _data_type == 'orders':
|
|
513
|
+
_result_data = self.merge_orders(self.data_connection_structure['orders'],
|
|
514
|
+
self.data_connection_structure['products'],
|
|
515
|
+
self.data_connection_structure['deliveries'])
|
|
516
|
+
else:
|
|
517
|
+
_result_data = self.get_data(conf=self.data_connection_structure['downloads'],
|
|
518
|
+
data_source_type='downloads')
|
|
519
|
+
if self.check_and_create_index(_data_type):
|
|
520
|
+
self.get_start_date()
|
|
521
|
+
if len(_result_data) != 0:
|
|
522
|
+
self.insert_to_index(data=_result_data, index=_data_type)
|
|
523
|
+
del _result_data
|
|
524
|
+
|
|
525
|
+
last_schedule_triggered_date = str(current_date_to_day())
|
|
526
|
+
self.update_schedule(date=last_schedule_triggered_date)
|
|
527
|
+
|
|
528
|
+
self.end_date = current_date_to_day()
|
|
529
|
+
|
|
530
|
+
spent_hour = round(abs(self.job_start_date - self.end_date).total_seconds() / 60 / 60, 2)
|
|
531
|
+
total_time_str = str(round(spent_hour, 2)) + " hr. " if spent_hour >= 1 else str(round(spent_hour * 60, 2)) + " min. "
|
|
532
|
+
comment = "indexes are created safely. Total spent time : " + total_time_str
|
|
533
|
+
self.logs_update(logs={"page": "data-execute",
|
|
534
|
+
"info": comment,
|
|
535
|
+
"color": "green"})
|
|
536
|
+
|
|
537
|
+
except Exception as e:
|
|
538
|
+
try: err_str = " - " + str(e).replace("'", " ")
|
|
539
|
+
except: err_str = " "
|
|
540
|
+
self.logs_update(logs={"page": "data-execute",
|
|
541
|
+
"info": "indexes Creation is failed! " + err_str,
|
|
542
|
+
"color": "red"})
|
|
543
|
+
|
|
544
|
+
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import logging
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
import sys, os, inspect
|
|
5
|
+
currentdir = os.path.dirname(os.path.abspath(inspect.getfile(inspect.currentframe())))
|
|
6
|
+
parentdir = os.path.dirname(currentdir)
|
|
7
|
+
sys.path.insert(0, parentdir)
|
|
8
|
+
|
|
9
|
+
from sqlalchemy import create_engine, MetaData
|
|
10
|
+
from os.path import abspath, join
|
|
11
|
+
import pandas as pd
|
|
12
|
+
from flask_login import current_user
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
from customeranalytics.utils import read_yaml, current_date_to_day, abspath_for_sample_data
|
|
16
|
+
|
|
17
|
+
engine = create_engine('sqlite://///' + join(abspath_for_sample_data(), "web", 'db.sqlite3'),
|
|
18
|
+
connect_args={'check_same_thread': False})
|
|
19
|
+
metadata = MetaData()
|
|
20
|
+
con = engine.connect()
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
class LogsBasicConfeger:
|
|
24
|
+
try: directory = pd.read_sql("select * from es_connection", con).to_dict('records')[-1]['directory']
|
|
25
|
+
except: directory = currentdir
|
|
26
|
+
|
|
27
|
+
try: user = current_user['email']
|
|
28
|
+
except: user = 'logs'
|
|
29
|
+
|
|
30
|
+
file_path = join(currentdir, "logs.log")
|
|
31
|
+
logging.basicConfig(filename=file_path,
|
|
32
|
+
level=logging.INFO,
|
|
33
|
+
format='%(asctime)s:%(levelname)s:%(message)s')
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
|