Browse Source

feat(crons): Update ruby onboarding for sidekiq auto discovery (#60600)

sidekiq is not a platform yet, so i added a panel to rails

closes #60567
Neel Shah 1 year ago
parent
commit
28469874d9

+ 16 - 1
static/app/views/monitors/components/cronsLandingPanel.tsx

@@ -31,6 +31,8 @@ import {
   NodeJsUpsertPlatformGuide,
   PHPUpsertPlatformGuide,
   QuickStartProps,
+  RubyRailsMixinPlatformGuide,
+  RubySidekiqAutoPlatformGuide,
   RubyUpsertPlatformGuide,
 } from './quickStartEntries';
 
@@ -38,6 +40,8 @@ enum GuideKey {
   BEAT_AUTO = 'beat_auto',
   UPSERT = 'upsert',
   MANUAL = 'manual',
+  MIXIN = 'mixin',
+  SIDEKIQ_AUTO = 'sidekiq_auto',
 }
 
 interface PlatformGuide {
@@ -98,7 +102,18 @@ const platformGuides: Record<SupportedPlatform, PlatformGuide[]> = {
       key: GuideKey.UPSERT,
     },
   ],
-  'ruby-rails': [],
+  'ruby-rails': [
+    {
+      Guide: RubySidekiqAutoPlatformGuide,
+      title: 'Sidekiq Auto Discovery',
+      key: GuideKey.SIDEKIQ_AUTO,
+    },
+    {
+      Guide: RubyRailsMixinPlatformGuide,
+      title: 'Mixin',
+      key: GuideKey.MIXIN,
+    },
+  ],
 };
 
 export function isValidPlatform(platform?: string | null): platform is SupportedPlatform {

+ 6 - 0
static/app/views/monitors/components/monitorQuickStartGuide.tsx

@@ -24,6 +24,7 @@ import {
   QuickStartProps,
   RubyCronQuickStart,
   RubyRailsCronQuickStart,
+  RubySidekiqCronQuickStart,
 } from 'sentry/views/monitors/components/quickStartEntries';
 
 import {Monitor} from '../types';
@@ -120,6 +121,11 @@ const onboardingGuides: Record<string, OnboardingGuide> = {
     Guide: RubyRailsCronQuickStart,
     platforms: new Set(['ruby', 'ruby-rails']),
   },
+  rubySidekiq: {
+    label: 'Sidekiq',
+    Guide: RubySidekiqCronQuickStart,
+    platforms: new Set(['ruby', 'ruby-rails']),
+  },
 };
 
 const guideToSelectOption = ({key, label}) => ({label, value: key});

+ 135 - 0
static/app/views/monitors/components/quickStartEntries.tsx

@@ -730,6 +730,101 @@ Sentry.capture_check_in(
   );
 }
 
+export function RubyRailsMixinPlatformGuide() {
+  const activeJobCode = `class ExampleActiveJob < ApplicationJob
+  include Sentry::Cron::MonitorCheckIns
+
+  # slug defaults to the job class name if not provided
+  sentry_monitor_check_ins slug: 'custom', monitor_config: Sentry::Cron::MonitorConfig.from_crontab('5 * * * *')
+
+  def perform(*args)
+    # do stuff
+  end
+end`;
+
+  const sidekiqJobCode = `class ExampleSidekiqJob
+  include Sidekiq::Job
+  include Sentry::Cron::MonitorCheckIns
+
+  # slug defaults to the job class name if not provided
+  sentry_monitor_check_ins slug: 'custom', monitor_config: Sentry::Cron::MonitorConfig.from_crontab('5 * * * *')
+
+  def perform(*args)
+    # do stuff
+  end
+end`;
+
+  const customCode = `# define the monitor config with an interval
+sentry_monitor_check_ins slug: 'custom', monitor_config: Sentry::Cron::MonitorConfig.from_interval(1, :minute)
+
+# define the monitor config with a crontab
+sentry_monitor_check_ins slug: 'custom', monitor_config: Sentry::Cron::MonitorConfig.from_crontab('5 * * * *')`;
+
+  return (
+    <Fragment>
+      <div>
+        {tct(
+          'You can use the mixin module from the [additionalDocs: Ruby SDK] to automatically capture check-ins from your jobs rather than creating them manually.',
+          {
+            additionalDocs: (
+              <ExternalLink href="https://docs.sentry.io/platforms/ruby/crons/#job-monitoring" />
+            ),
+          }
+        )}
+      </div>
+      <div>{t('ActiveJob Example:')}</div>
+      <CodeSnippet language="ruby">{activeJobCode}</CodeSnippet>
+      <div>{t('Sidekiq Example:')}</div>
+      <CodeSnippet language="ruby">{sidekiqJobCode}</CodeSnippet>
+      <div>
+        {t(
+          'You must pass in the monitor config explicity for upserts or you must create a new monitor explicitly in the UI.'
+        )}
+      </div>
+      <CodeSnippet language="ruby">{customCode}</CodeSnippet>
+    </Fragment>
+  );
+}
+
+export function RubySidekiqAutoPlatformGuide() {
+  const sidekiqCronCode = `Sentry.init do |config|
+  # for sidekiq-cron
+  config.enabled_patches += [:sidekiq_cron]
+
+  # for sidekiq-scheduler
+  config.enabled_patches += [:sidekiq_scheduler]
+end`;
+
+  return (
+    <Fragment>
+      <div>
+        {tct(
+          'If you use gems such as [sidekiqCronLink:sidekiq-cron] or [sidekiqSchedulerLink:sidekiq-scheduler] to manage your scheduled jobs, Sentry can automatically monitor all of them for you without any additional configuration.',
+          {
+            sidekiqCronLink: (
+              <ExternalLink href="https://github.com/sidekiq-cron/sidekiq-cron" />
+            ),
+            sidekiqSchedulerLink: (
+              <ExternalLink href="https://github.com/sidekiq-scheduler/sidekiq-scheduler" />
+            ),
+          }
+        )}
+      </div>
+      <div>
+        {tct(
+          '[installLink:Install and configure] the Sentry Ruby and Sidekiq SDKs (min v5.14.0) and turn on the relevant patches:',
+          {
+            installLink: (
+              <ExternalLink href="https://docs.sentry.io/platforms/ruby/guides/sidekiq/" />
+            ),
+          }
+        )}
+      </div>
+      <CodeSnippet language="ruby">{sidekiqCronCode}</CodeSnippet>
+    </Fragment>
+  );
+}
+
 export function RubyCronQuickStart(props: QuickStartProps) {
   const {slug} = withDefaultProps(props);
 
@@ -799,3 +894,43 @@ sentry_monitor_check_ins slug: '${slug}', monitor_config: Sentry::Cron::MonitorC
     </Fragment>
   );
 }
+
+export function RubySidekiqCronQuickStart(props: QuickStartProps) {
+  const {slug} = withDefaultProps(props);
+
+  const mixinCode = `class ExampleJob
+  incude Sidekiq::Job
+  include Sentry::Cron::MonitorCheckIns
+
+  # slug defaults to the job class name
+  sentry_monitor_check_ins slug: '${slug}'
+
+  def perform(*args)
+    # do stuff
+  end
+end`;
+
+  const customCode = `# define the monitor config with an interval
+sentry_monitor_check_ins slug: '${slug}', monitor_config: Sentry::Cron::MonitorConfig.from_interval(1, :minute)
+
+# define the monitor config with a crontab
+sentry_monitor_check_ins slug: '${slug}', monitor_config: Sentry::Cron::MonitorConfig.from_crontab('5 * * * *')`;
+
+  return (
+    <Fragment>
+      <div>
+        {tct(
+          '[installLink:Install and configure] the Sentry Ruby and Sidekiq SDKs (min v5.12.0), then instrument your job with our mixin module:',
+          {
+            installLink: (
+              <ExternalLink href="https://docs.sentry.io/platforms/ruby/guides/sidekiq/" />
+            ),
+          }
+        )}
+      </div>
+      <CodeSnippet language="ruby">{mixinCode}</CodeSnippet>
+      <div>{t('You can pass in optional attributes as follows:')}</div>
+      <CodeSnippet language="ruby">{customCode}</CodeSnippet>
+    </Fragment>
+  );
+}