AWS Lambda Production Monitoring ve Debugging: Kanıtlanmış Stratejiler
AWS Lambda'yı production için enstrümente edin: CloudWatch custom metrics, X-Ray tracing, structured logging ve business etkisini izleyen alert'ler.
Lambda function’ları production’da sessizce başarısız olur; varsayılan CloudWatch metrikleri, cold-start gürültüsü ve eksik distributed trace’ler bir araya geldiğinde kök nedeni gizler. Yapılandırılmış bir observability stratejisi olmadan debugging, veri odaklı analizden baskı altında tahmine kayar. Çoğu Lambda iş yükünde işe yarayan kurulum küçüktür: business sonuçlarına bağlanmış custom metrikler, X-Ray active tracing ve her satırında request ID taşıyan JSON log’lar.
Bu üç sinyal farklı işleri görür. Metrikler bir şeyin bozulduğunu, trace’ler nerede bozulduğunu, log’lar ise nedenini söyler. Birini eksik bıraktığınızda diğer ikisi en kötü anda ortaya çıkan bir boşluk bırakır: hata log’lamadan timeout’a düşen bir ödeme handler’ı ya da hiçbir alarmı tetiklemeyen bir retry fırtınası.
Lambda Observability’nin Üç Direği#
1. Metrikler: Erken Uyarı Sistemi#
Mutlaka Monitor Etmeniz Gereken Metrikler:
// Lambda observability için custom metrikler
// Node.js 20.x ve 22.x runtime'ları ile uyumlu
import { CloudWatch } from '@aws-sdk/client-cloudwatch';
const cloudwatch = new CloudWatch({});
export const publishCustomMetrics = async (
functionName: string,
duration: number,
success: boolean,
businessContext?: { userId?: string, feature?: string }
) => {
const metrics = [
{
MetricName: 'FunctionDuration',
Value: duration,
Unit: 'Milliseconds',
Dimensions: [
{ Name: 'FunctionName', Value: functionName },
{ Name: 'Feature', Value: businessContext?.feature || 'unknown' }
]
},
{
MetricName: success ? 'FunctionSuccess' : 'FunctionFailure',
Value: 1,
Unit: 'Count',
Dimensions: [
{ Name: 'FunctionName', Value: functionName }
]
}
];
// Business-specific metrikler. userId'yi dimension'lardan uzak tutun:
// her farklı dimension kombinasyonu ayrı bir custom metric olarak
// faturalanır, yani bir user ID tek metriği kullanıcı başına bir metriğe çevirir.
if (businessContext?.userId) {
metrics.push({
MetricName: 'UserAction',
Value: 1,
Unit: 'Count',
Dimensions: [
{ Name: 'FunctionName', Value: functionName },
{ Name: 'ActionType', Value: success ? 'completed' : 'failed' }
]
});
}
await cloudwatch.putMetricData({
Namespace: 'Lambda/Business',
MetricData: metrics
});
};
2. Trace’ler: İstek Akışı#
X-Ray, kendi enstrümente etmediğiniz servislere giden çağrılar dahil tüm istek yolunu gösterir:
import AWSXRay from 'aws-xray-sdk-core';
import { DynamoDBClient } from '@aws-sdk/client-dynamodb';
import { DynamoDBDocumentClient } from '@aws-sdk/lib-dynamodb';
// AWS SDK v3'u instrument et
const dynamoClient = AWSXRay.captureAWSv3Client(new DynamoDBClient({}));
const dynamoDB = DynamoDBDocumentClient.from(dynamoClient);
// Active tracing açıkken segment'i handler çalışmadan önce Lambda açar.
// captureAsyncFunc callback'ini hemen çalıştırır; bu yüzden handler'ın
// içinde belirli bir çağrının etrafında kullanılır, export'un etrafında değil.
export const handler = async (event: any) => {
// Filtreleme için custom annotation'lar ekle
const segment = AWSXRay.getSegment();
segment?.addAnnotation('userId', event.userId);
segment?.addAnnotation('paymentMethod', event.paymentMethod);
segment?.addAnnotation('environment', process.env.STAGE);
// External API call'ları trace et
const subsegment = segment?.addNewSubsegment('payment-provider-api');
try {
const paymentResult = await processPayment(event);
subsegment?.close();
// Business metadata ekle
segment?.addMetadata('payment', {
amount: event.amount,
currency: event.currency,
processingTime: Date.now() - event.timestamp
});
return { success: true, paymentId: paymentResult.id };
} catch (error) {
// Hatayla kapatmak subsegment'in açık kalmasını engeller
subsegment?.close(error as Error);
segment?.addError(error as Error);
segment?.addMetadata('errorContext', {
userId: event.userId,
errorType: (error as Error).name,
requestId: event.requestId
});
throw error;
}
};
3. Log’lar: Tarihsel Kayıt#
İşe Yarar Structured Logging Pattern’i:
import { createLogger, format, transports } from 'winston';
const logger = createLogger({
level: process.env.LOG_LEVEL || 'info',
format: format.combine(
format.timestamp(),
format.errors({ stack: true }),
format.json()
),
transports: [
new transports.Console()
]
});
// Lambda context-aware logging
export const createContextLogger = (context: any, event: any) => {
const requestId = context.awsRequestId;
const functionName = context.functionName;
return {
info: (message: string, meta?: any) => logger.info({
message,
requestId,
functionName,
stage: process.env.STAGE,
...meta
}),
error: (message: string, error?: Error, meta?: any) => logger.error({
message,
error: error?.stack || error?.message,
requestId,
functionName,
stage: process.env.STAGE,
...meta
}),
// Business event logging
business: (event: string, data: any) => logger.info({
message: `Business Event: ${event}`,
businessEvent: event,
data,
requestId,
functionName,
timestamp: new Date().toISOString()
})
};
};
// Handler'da kullanım
export const handler = async (event: any, context: any) => {
const log = createContextLogger(context, event);
log.info('Function invoked', { eventType: event.Records?.[0]?.eventName });
try {
const result = await processEvent(event);
log.business('order-processed', { orderId: result.orderId, amount: result.amount });
return result;
} catch (error) {
log.error('Processing failed', error as Error, { eventData: event });
throw error;
}
};
CloudWatch Dashboard Kurulumu#
Stakeholder İletişimi için Business Dashboard#
Stakeholder’lar sistem sağlığı konusunda görünürlük istediğinde, teknik detaylardan çok business odaklı metrikleri göstermek daha değerli oluyor:
# Business odaklı dashboard için CloudFormation template
Resources:
BusinessDashboard:
Type: AWS::CloudWatch::Dashboard
Properties:
DashboardName: "Lambda-Business-Health"
DashboardBody: !Sub |
{
"widgets": [
{
"type": "metric",
"properties": {
"metrics": [
["Lambda/Business", "OrdersProcessed", "FunctionName", "order-processor"],
["Lambda/Business", "PaymentsCompleted", "FunctionName", "payment-processor"],
["Lambda/Business", "UserRegistrations", "FunctionName", "user-registration"]
],
"period": 300,
"stat": "Sum",
"region": "${AWS::Region}",
"title": "Business Transactions (Last 24h)"
}
},
{
"type": "metric",
"properties": {
"metrics": [
["AWS/Lambda", "Errors", "FunctionName", "order-processor"],
["AWS/Lambda", "Throttles", "FunctionName", "payment-processor"]
],
"period": 300,
"stat": "Sum",
"region": "${AWS::Region}",
"title": "System Health Issues"
}
}
]
}
Debugging için Teknik Dashboard#
TechnicalDashboard:
Type: AWS::CloudWatch::Dashboard
Properties:
DashboardName: "Lambda-Technical-Deep-Dive"
DashboardBody: !Sub |
{
"widgets": [
{
"type": "metric",
"properties": {
"metrics": [
["AWS/Lambda", "Duration", "FunctionName", "payment-processor", { "stat": "Average" }],
["AWS/Lambda", "Duration", "FunctionName", "payment-processor", { "stat": "p99" }]
],
"period": 60,
"region": "${AWS::Region}",
"title": "Function Duration (Average vs P99)"
}
},
{
"type": "log",
"properties": {
"query": "SOURCE '/aws/lambda/payment-processor'\n| fields @timestamp, @message, @requestId\n| filter @message like /ERROR/\n| sort @timestamp desc\n| limit 100",
"region": "${AWS::Region}",
"title": "Recent Errors (Last 1 Hour)"
}
}
]
}
Alerting Stratejileri#
Business Etkisine Dayalı Alert’ler#
Her şeye değil, business etkisine alert verin:
# CloudFormation alert konfigürasyonu
Resources:
# Kritik: Ödeme işleme hataları
PaymentFailureAlarm:
Type: AWS::CloudWatch::Alarm
Properties:
AlarmName: "Lambda-PaymentProcessor-CriticalFailures"
AlarmDescription: "Payment processing failures above threshold"
MetricName: Errors
Namespace: AWS/Lambda
Statistic: Sum
Period: 300
EvaluationPeriods: 2
Threshold: 5 # 10 dakikada 5'ten fazla hata
ComparisonOperator: GreaterThanThreshold
Dimensions:
- Name: FunctionName
Value: !Ref PaymentProcessorFunction
AlarmActions:
- !Ref CriticalAlertTopic
TreatMissingData: notBreaching
# Uyarı: Normalden yavaş işlem
PaymentLatencyAlarm:
Type: AWS::CloudWatch::Alarm
Properties:
AlarmName: "Lambda-PaymentProcessor-HighLatency"
MetricName: Duration
Namespace: AWS/Lambda
Statistic: Average
Period: 300
EvaluationPeriods: 3
Threshold: 5000 # 5 saniye ortalama
ComparisonOperator: GreaterThanThreshold
AlarmActions:
- !Ref WarningAlertTopic
# Genel sistem sağlığı için composite alarm
SystemHealthAlarm:
Type: AWS::CloudWatch::CompositeAlarm
Properties:
AlarmName: "Lambda-SystemHealth-Critical"
AlarmRule: !Sub |
ALARM("${PaymentFailureAlarm}") OR
ALARM("${OrderProcessingAlarm}") OR
ALARM("${DatabaseConnectionAlarm}")
AlarmActions:
- !Ref EmergencyAlertTopic
Timeout’a Yaklaşma Tespiti#
Timeout’lar Errors metriğine yansımadan çok önce Duration sıçraması olarak görünür. Bu metrik, invocation’ın raporlayacak bütçesi hâlâ varken tetiklenir:
export const detectNearTimeout = async (functionName: string, context: any) => {
const remainingTime = context.getRemainingTimeInMillis();
// Bir saniyeden az bütçe kaldı: yavaş bir dependency çağrısı invocation'ı bitirir
if (remainingTime < 1000) {
await cloudwatch.putMetricData({
Namespace: 'Lambda/Performance',
MetricData: [{
MetricName: 'NearTimeout',
Value: 1,
Unit: 'Count',
// remainingTime dimension'a girmez; milisaniye değeri olarak
// neredeyse her invocation'da yeni bir custom metric yaratır
Dimensions: [
{ Name: 'FunctionName', Value: functionName }
]
}]
});
}
};
Error Handling ve Dead Letter Queue’lar#
Stratejik Error Handling#
// Daha iyi debugging için error kategorilendirmesi
export enum ErrorCategory {
TRANSIENT = 'TRANSIENT', // Retry mantıklı
CLIENT_ERROR = 'CLIENT_ERROR', // Kullanıcı input sorunu
SYSTEM_ERROR = 'SYSTEM_ERROR', // Altyapı problemi
BUSINESS_ERROR = 'BUSINESS_ERROR' // Business logic ihlali
}
export class CategorizedError extends Error {
constructor(
message: string,
public category: ErrorCategory,
public retryable: boolean = false,
public context?: any
) {
super(message);
this.name = 'CategorizedError';
}
}
export const handleError = async (error: Error, event: any, context: any) => {
const log = createContextLogger(context, event);
if (error instanceof CategorizedError) {
// Kategorilere göre error handle et
switch (error.category) {
case ErrorCategory.TRANSIENT:
log.info('Transient error - will retry', {
error: error.message,
retryable: error.retryable
});
throw error; // Lambda retry mekanizmasının handle etmesini sağla
case ErrorCategory.CLIENT_ERROR:
log.info('Client error - no retry needed', { error: error.message });
return {
statusCode: 400,
body: JSON.stringify({ error: 'Invalid request' })
};
case ErrorCategory.SYSTEM_ERROR:
log.error('System error detected', error, {
requiresInvestigation: true
});
// İnceleme için DLQ'ya gönder
throw error;
case ErrorCategory.BUSINESS_ERROR:
log.business('business-rule-violation', {
rule: error.message,
context: error.context
});
return {
statusCode: 422,
body: JSON.stringify({ error: error.message })
};
}
} else {
// Bilinmeyen error - system error olarak ele al
log.error('Uncategorized error', error);
throw new CategorizedError(
error.message,
ErrorCategory.SYSTEM_ERROR,
false,
{ originalError: error.stack }
);
}
};
Dead Letter Queue Analizi#
// Error pattern analizi için DLQ processor
export const dlqProcessor = async (event: any, context: any) => {
const log = createContextLogger(context, event);
for (const record of event.Records) {
try {
const failedEvent = JSON.parse(record.body);
const errorInfo = {
functionName: record.eventSourceARN?.split(':')[6],
errorCount: record.attributes?.ApproximateReceiveCount || '1',
// Lambda başarısız async event'i DLQ'ya yazarken RequestID, ErrorCode
// ve ErrorMessage'ı SQS message attribute'u olarak ekler
errorCode: record.messageAttributes?.ErrorCode?.stringValue || 'unknown',
failureReason: record.messageAttributes?.ErrorMessage?.stringValue || 'unknown',
originalTimestamp: failedEvent.timestamp,
retryCount: parseInt(record.attributes?.ApproximateReceiveCount || '0')
};
// Pattern detection
if (errorInfo.retryCount > 3) {
log.business('recurring-failure-pattern', {
pattern: 'high-retry-count',
functionName: errorInfo.functionName,
suggestion: 'investigate-configuration'
});
}
// Analiz için sakla
await storeErrorPattern(errorInfo, failedEvent);
} catch (processingError) {
log.error('Failed to process DLQ record', processingError as Error);
}
}
};
İleri Seviye Debugging Teknikleri#
Lambda Function URL Debugging#
// Production troubleshooting için debug endpoint
export const debugHandler = async (event: any, context: any) => {
// Sadece non-production'da veya özel header ile izin ver
const allowDebug = process.env.STAGE !== 'prod' ||
event.headers?.['x-debug-token'] === process.env.DEBUG_TOKEN;
if (!allowDebug) {
return { statusCode: 403, body: 'Debug access denied' };
}
const debugInfo = {
environment: {
stage: process.env.STAGE,
region: context.invokedFunctionArn.split(':')[3],
memorySize: context.memoryLimitInMB,
remainingTimeMs: context.getRemainingTimeInMillis()
},
runtime: {
nodeVersion: process.version,
platform: process.platform,
uptime: process.uptime()
},
lastErrors: await getRecentErrors(context.functionName),
healthChecks: {
database: await checkDatabaseConnection(),
externalAPI: await checkExternalServices(),
memory: process.memoryUsage()
}
};
return {
statusCode: 200,
body: JSON.stringify(debugInfo, null, 2)
};
};
Production’da Performance Profiling#
// Güvenli production profiling
export const profileHandler = (originalHandler: Function) => {
return async (event: any, context: any) => {
const shouldProfile = Math.random() < 0.01; // Request'lerin %1'ini profile et
if (!shouldProfile) {
return originalHandler(event, context);
}
const startTime = Date.now();
const startMemory = process.memoryUsage();
try {
const result = await originalHandler(event, context);
const endTime = Date.now();
const endMemory = process.memoryUsage();
// Profiling datasını gönder
await cloudwatch.putMetricData({
Namespace: 'Lambda/Profiling',
MetricData: [
{
MetricName: 'ExecutionDuration',
Value: endTime - startTime,
Unit: 'Milliseconds'
},
{
MetricName: 'MemoryUsed',
Value: endMemory.heapUsed - startMemory.heapUsed,
Unit: 'Bytes'
}
]
});
return result;
} catch (error) {
// Error senaryolarını da profile et
const errorTime = Date.now();
await cloudwatch.putMetricData({
Namespace: 'Lambda/Profiling',
MetricData: [{
MetricName: 'ErrorDuration',
Value: errorTime - startTime,
Unit: 'Milliseconds'
}]
});
throw error;
}
};
};
Troubleshooting Workflow’ları#
5 Dakikalık Debug Protokolü#
Peak trafik sırasında işler ters gittiğinde sistematik bir yaklaşıma ihtiyacınız var:
// Acil durum debug checklist'i
export const emergencyDebugChecklist = {
step1_quickHealth: async (functionName: string) => {
const metrics = await cloudwatch.getMetricStatistics({
Namespace: 'AWS/Lambda',
MetricName: 'Errors',
Dimensions: [{ Name: 'FunctionName', Value: functionName }],
StartTime: new Date(Date.now() - 10 * 60 * 1000), // Son 10 dakika
EndTime: new Date(),
Period: 300,
Statistics: ['Sum']
});
return {
recentErrors: metrics.Datapoints?.reduce((sum, dp) => sum + (dp.Sum || 0), 0),
timeframe: 'last-10-minutes'
};
},
step2_checkDependencies: async () => {
return {
database: await checkDatabaseConnection(),
externalAPIs: await checkExternalServices(),
downstream: await checkDownstreamServices()
};
},
step3_analyzeLogs: async (functionName: string) => {
// Son hatalar için CloudWatch Logs Insights query
const query = `
fields @timestamp, @message, @requestId
| filter @message like /ERROR/ or @message like /TIMEOUT/
| sort @timestamp desc
| limit 20
`;
// Implementation CloudWatch Logs API kullanacak
return { recentErrorPatterns: 'implementation-needed' };
}
};
Memory Leak Detection#
// Uzun çalışan Lambda container'larında memory leak tespiti
let requestCount = 0;
const memorySnapshots: Array<{ count: number; memory: NodeJS.MemoryUsage }> = [];
export const memoryTrackingWrapper = (handler: Function) => {
return async (event: any, context: any) => {
requestCount++;
const beforeMemory = process.memoryUsage();
const result = await handler(event, context);
const afterMemory = process.memoryUsage();
// Request'ler boyunca memory artışını takip et
if (requestCount % 10 === 0) {
memorySnapshots.push({ count: requestCount, memory: afterMemory });
// Buffer'ı sınırla ki leak dedektörü kendisi leak yapmasın
if (memorySnapshots.length > 20) memorySnapshots.shift();
if (memorySnapshots.length > 10) {
const oldSnapshot = memorySnapshots[memorySnapshots.length - 10];
const currentSnapshot = memorySnapshots[memorySnapshots.length - 1];
const heapGrowth = currentSnapshot.memory.heapUsed - oldSnapshot.memory.heapUsed;
if (heapGrowth > 50 * 1024 * 1024) { // 50MB artış
await cloudwatch.putMetricData({
Namespace: 'Lambda/MemoryLeak',
MetricData: [{
MetricName: 'SuspectedMemoryLeak',
Value: heapGrowth,
Unit: 'Bytes',
Dimensions: [
{ Name: 'FunctionName', Value: context.functionName }
]
}]
});
}
}
}
return result;
};
};
Maliyete Duyarlı Monitoring#
Yüksek Hacimli Function’lar için Sampling Stratejisi#
// Business değerine dayalı akıllı sampling
export const createSampler = (baseSampleRate: number = 0.01) => {
return (event: any): boolean => {
// Her zaman error'ları sample et
if (event.errorType) return true;
// Her zaman yüksek değerli transaction'ları sample et
if (event.transactionValue > 1000) return true;
// Yeni kullanıcıları daha sık sample et
if (event.userType === 'new') return Math.random() < baseSampleRate * 5;
// Normal sampling
return Math.random() < baseSampleRate;
};
};
const sampler = createSampler(0.005); // %0.5 base rate
export const handler = async (event: any, context: any) => {
const shouldMonitor = sampler(event);
if (shouldMonitor) {
// Tam monitoring ve tracing
return AWSXRay.captureAsyncFunc('handler', async () => {
return processWithFullLogging(event, context);
});
} else {
// Minimal monitoring
return processWithBasicLogging(event, context);
}
};
Log Retention Stratejisi#
# Log önemine göre farklı retention süresi
Resources:
BusinessLogGroup:
Type: AWS::Logs::LogGroup
Properties:
LogGroupName: !Sub "/aws/lambda/${BusinessProcessorFunction}"
RetentionInDays: 90 # Business log'ları daha uzun tut
DebugLogGroup:
Type: AWS::Logs::LogGroup
Properties:
LogGroupName: !Sub "/aws/lambda/${UtilityFunction}"
RetentionInDays: 7 # Debug log'ları daha kısa olabilir
Bir Sonraki Bölüm: Advanced Pattern’ler ve Maliyet Optimizasyonu#
Bu serinin son bölümü, hem karmaşıklığı hem de maliyeti azaltan advanced Lambda pattern’lerini ele alıyor:
- Multi-tenant mimari pattern’leri
- Event-driven maliyet optimizasyonu
- Advanced deployment stratejileri
- Performance vs maliyet trade-off’ları
Bu Kurulum Ne Zaman Yeterli#
Custom business metrikleri, active X-Ray tracing ve JSON log’lar çoğu Lambda iş yükünde neyin, nerede ve neden bozulduğunu üçüncü parti bir agent çalıştırmadan yanıtlar. İki durum fazlasını gerektirir. Bir istek çok sayıda servisten geçiyorsa ve X-Ray sampling ihtiyacınız olan trace’i sürekli düşürüyorsa, ADOT Lambda layer’ı üzerinden OpenTelemetry’ye geçin ve span’ları hepsini saklayan bir backend’e gönderin. Senkron putMetricData çağrısı function duration’ınızda görünmeye başladıysa Embedded Metric Format’a geçin: metrik zaten yazdığınız bir log satırının içinde taşınır ve invocation’ı bloklamaz. Custom metric ücretleri her iki yolda da aynı kalır, yani cardinality disiplini yine geçerlidir. Üç sinyalle başlayın; bu ikisini ancak belirli bir soru yanıtsız kalmaya devam ettiğinde ekleyin.
Kaynaklar#
- Monitoring and observability - AWS Lambda (yeni sekmede açılır) - CloudWatch metrikleri, X-Ray izleme, CloudWatch Logs ve Application Signals dahil tüm Lambda izleme araçlarına genel bakış.
- Visualize Lambda function invocations using AWS X-Ray (yeni sekmede açılır) - Servis haritaları ve aranabilir iz özetleri oluşturmak için Lambda’da X-Ray aktif izlemenin etkinleştirilmesi.
- Using CloudWatch metrics with Lambda (yeni sekmede açılır) - Errors, Throttles, Duration ve ConcurrentExecutions dahil CloudWatch’a otomatik gönderilen Lambda metriklerinin tam listesi.
- Types of metrics for Lambda functions (yeni sekmede açılır) - Üretim uyarıları ve olay müdahalesi için en önemli metrikleri ele alan Lambda Operator Guide.
- Logging and metrics for AWS Lambda - AWS Prescriptive Guidance (yeni sekmede açılır) - Lambda için yapılandırılmış kayıt desenleri, günlük saklama stratejileri ve CloudWatch Logs Insights sorgu örnekleri.
- Monitor application performance with Amazon CloudWatch Application Signals (yeni sekmede açılır) - Hizmet düzeyinde panolar ve RED metrikleri için ADOT Lambda katmanı üzerinden otomatik enstrümantasyon.
- Recommended alarms - Amazon CloudWatch (yeni sekmede açılır) - Errors, Throttles, Duration ve IteratorAge eşikleri dahil Lambda için AWS tarafından önerilen alarm yapılandırmaları.
- Embedding metrics within logs - Amazon CloudWatch (yeni sekmede açılır) - Her invocation’da PutMetricData çağırmak yerine custom metrikleri yapılandırılmış log event’lerinin içinde yayınlama ve yüksek cardinality uyarısı.
- Capturing records of Lambda asynchronous invocations (yeni sekmede açılır) - Dead-letter queue kurulumu ve Lambda’nın başarısız async event’lere eklediği message attribute’ları: RequestID, ErrorCode ve ErrorMessage.
AWS Lambda Production Rehberi: 5 Yıllık Gerçek Dünya Deneyimi
5+ yıllık production deneyimine dayalı kapsamlı AWS Lambda rehberi. Cold start optimizasyonu, performans ayarlama, monitoring ve maliyet optimizasyonu ile gerçek savaş hikayeleri ve pratik çözümler.
Bu serideki tüm yazılar
İlgili yazılar
Yeşil ışıklı dashboard'lardan, dağıtık izleme ile sistem davranışını ve iş etkisini anlatan observability sistemlerine geçişin yolu.
observability · monitoring · opentelemetry +3
Yüksek riskli üretim ortamlarında bildirim sistemi hatalarından edinilen gerçek dünya debugging teknikleri, izleme stratejileri ve dersler
debugging · monitoring · production +4
Bir kodlama ajanının evi olarak devcontainer, Codespaces ve AWS Lambda MicroVM: her basamak ne katıyor ve ajanı laptoptan çıkarmak ne zaman kazandırıyor.
lambda · claude-code · ai-tools +5
İç servis katmanı kurmadan önce kurup kurmayacağınıza karar verin. Katmanın çağrı başına maliyeti, VPC Lattice'in kazandığı hacim ve direct invoke'un hâlâ kazandığı an.
aws · aws-cdk · lambda +4
Private REST API gRPC’yi yapısal olarak taşıyamaz ve gRPC konuşan her AWS yüzeyi Lambda hedeflerini dışlar. gRPC’den neyi tutmalı, neyi bırakmalı.
aws · aws-cdk · lambda +4