Overview

Vidly is a video rental store web application built with ASP.NET MVC 5 that demonstrates core MVC architectural patterns including routing, controllers, models, view models, and Razor views.

Key Features

Tech Stack

ComponentTechnology
FrameworkASP.NET MVC 5.2.3
Runtime.NET Framework 4.5.2
View EngineRazor
CSSBootstrap 3 (Lumen theme)
JavaScriptjQuery 1.10.2
TestingMSTest + Coverlet
CI/CDGitHub Actions

Installation

Prerequisites

Clone & Setup

git clone https://github.com/sauravbhattacharya001/Vidly.git
cd Vidly

Restore Dependencies

In Visual Studio:

Build → Restore NuGet Packages

Or via CLI:

nuget restore Vidly.sln

Run

Press F5 in Visual Studio to launch with IIS Express. The application starts at http://localhost:51355/.

Quick Start

After launching the application:

  1. Navigate to /movies to see the movie catalog
  2. Click Create New to add a movie (name + optional release date)
  3. Edit or delete movies from the listing page
  4. Visit /movies/random for a random movie recommendation
  5. Try /movies/released/2024/01 to filter by release date

Project Structure

Vidly.sln ├── Vidly/ ← Main web application │ ├── Controllers/ │ │ ├── HomeController.cs Landing, About, Contact │ │ ├── MoviesController.cs Movie CRUD + filtering │ │ ├── RentalsController.cs Checkout, return, delete │ │ ├── DashboardController.cs Analytics dashboard │ │ └── ... (10+ controllers) │ ├── Models/ │ │ ├── Movie.cs Movie entity + validation │ │ ├── Customer.cs Customer entity + validation │ │ ├── Rental.cs Rental entity + status tracking │ │ └── ... (enums, view models) │ ├── Services/ ← 33 business services │ │ ├── PricingService.cs Rate calculation + tier benefits │ │ ├── RentalReturnService.cs Return workflow + late fees │ │ ├── DashboardService.cs Single-pass analytics │ │ └── ... (see Service Catalog) │ ├── Repositories/ │ │ ├── IRepository.cs Generic CRUD interface │ │ ├── IMovieRepository.cs Movie-specific queries │ │ └── InMemoryMovieRepository Thread-safe in-memory store │ ├── Utilities/ │ │ ├── SortHelper.cs Declarative sorting │ │ └── JsonSerializer.cs JSON serialization │ ├── Filters/ │ │ └── RateLimitAttribute.cs Rate limiting filter │ ├── Views/ Razor views │ ├── App_Start/ Config (routes, bundles, filters) │ ├── Content/ CSS assets │ └── Scripts/ JavaScript assets │ └── Vidly.Tests/ ← 2,389 unit tests (59 files) ├── Models/ Model validation tests ├── ViewModels/ ViewModel tests ├── Controllers/ Controller tests └── Services/ Service logic + edge cases

Design Patterns

🏗️ Repository Pattern

Data access is abstracted behind IRepository<T> and IMovieRepository interfaces. The InMemoryMovieRepository provides a thread-safe implementation using ConcurrentDictionary with additional locking for atomic operations.

💉 Dependency Injection

MoviesController uses constructor injection, accepting an IMovieRepository. The parameterless constructor provides a default in-memory implementation, while tests inject mocks/fakes for isolation.

📦 View Model Pattern

RandomMovieViewModel composes a Movie with a list of Customer objects, enabling the view to render data from multiple domain entities without coupling to the models directly.

🔒 Thread Safety

The in-memory repository uses lock statements for operations like Add, Update, and Remove that need atomicity (e.g., incrementing the ID counter). Read operations are lock-free via ConcurrentDictionary.

Models

Movie

PropertyTypeValidation
IdintAuto-assigned
NamestringRequired, max 255 chars
ReleaseDateDateTime?Optional

Customer

PropertyTypeValidation
IdintAuto-assigned
NamestringRequired, max 255 chars

RandomMovieViewModel

PropertyTypeDescription
MovieMovieThe randomly selected movie
CustomersList<Customer>Associated customers

Routes

MethodRouteDescription
GET/Home page
GET/moviesMovie listing (pagination + sorting)
GET/movies/randomRandom movie showcase
GET/movies/createNew movie form
POST/movies/createSubmit new movie
GET/movies/edit/{id}Edit movie form
POST/movies/edit/{id}Submit movie edits
POST/movies/delete/{id}Delete a movie
GET/movies/released/{year}/{month}Filter by release date

URL Parameters

ParameterTypeDescription
pageIndexintPage number (default: 1)
sortBystringName (default) or Id
yearintRelease year (1888–2100)
monthintRelease month (01–12)

Controllers

MoviesController

Handles all movie CRUD operations. Uses constructor injection with IMovieRepository.

public class MoviesController : Controller
{
    private readonly IMovieRepository _movieRepository;

    // Default: uses InMemoryMovieRepository
    public MoviesController() : this(new InMemoryMovieRepository()) { }

    // DI-ready: accepts any IMovieRepository
    public MoviesController(IMovieRepository movieRepository)
    {
        _movieRepository = movieRepository
            ?? throw new ArgumentNullException(nameof(movieRepository));
    }
}

HomeController

Serves the landing page, About, and Contact views. Standard MVC controller with no custom logic.

Repositories

Interface Hierarchy

IRepository<T> ← Generic CRUD interface │ GetAll() │ GetById(id) │ Add(entity) │ Update(entity) │ Remove(id) │ └── IMovieRepository ← Movie-specific queries │ GetByReleaseDate(year, month) │ GetRandom() │ └── InMemoryMovieRepository ← Thread-safe implementation Uses ConcurrentDictionary + lock

Thread Safety

The InMemoryMovieRepository uses a two-layer approach:

Testing

Running Tests

# Restore and run
dotnet restore Vidly.Tests/Vidly.Tests.csproj
dotnet test Vidly.Tests/Vidly.Tests.csproj

# With coverage
dotnet test Vidly.Tests/Vidly.Tests.csproj --collect:"XPlat Code Coverage"

Test Suite (2,389 Tests across 59 Files)

CategoryCoverage
Model & ViewModel TestsValidation, required fields, string length, defaults, composition
Controller TestsAll 10+ controllers: routing, authorization, error handling, edge cases
Service TestsAll 33 services: business logic, boundary conditions, error paths
Repository TestsIn-memory repositories: CRUD, thread safety, search, pagination
Security TestsExport safety, rate limiting, anti-forgery, input validation

Coverage Reports

Coverage reports are generated in Cobertura XML format and uploaded as CI artifacts on every push to master.

CI/CD Pipeline

The project uses GitHub Actions for continuous integration:

⚙️ Build & Test Workflow

Triggered on every push to master and on pull requests.

  • Runs on windows-latest with .NET SDK 8.0
  • Restores NuGet packages
  • Builds in Release configuration
  • Runs all 2,389 tests with code coverage
  • Uploads test results (TRX) and coverage (Cobertura) as artifacts
  • Outputs coverage summary in the workflow logs

Contributing

  1. Fork the repository
  2. Create a feature branch: git checkout -b feature/your-feature
  3. Write tests for new functionality
  4. Commit your changes: git commit -m "Add your feature"
  5. Push: git push origin feature/your-feature
  6. Open a Pull Request

Code Style

Service Catalog

Vidly includes 33 business services organized into five domains. All services use constructor injection with repository interfaces and follow in-memory, list-based storage patterns.

🎬 Core Rental Operations

PricingService

Calculates daily rental rates with membership discounts, new-release premiums, and per-movie overrides. Provides GetMovieDailyRate() and GetBenefits() for tier-based pricing.

RentalReturnService

Orchestrates the return workflow: late-fee calculation with tier-based grace periods, condition assessment and damage charges, loyalty-point awards, and batch return processing.

RentalHistoryService

Filtered rental history queries, customer timelines, popular rental times, retention metrics, inventory forecasting, and loyalty score computation.

InventoryService

Real-time stock tracking, availability checks, low-stock alerts, and inventory audit reports.

ReservationService

Hold movies for customers with expiry management and conflict detection.

👥 Customer Management

MembershipTierService

Tier evaluation (Basic → Silver → Gold → Platinum) with upgrade/downgrade logic, benefit lookups, and renewal management.

LoyaltyPointsService

Point accrual, redemption, tier multipliers, transaction history, and balance queries.

CustomerSegmentationService

RFM analysis (Recency, Frequency, Monetary), customer clustering, and segment-based marketing insights.

CustomerActivityService

Activity feeds, engagement tracking, and customer lifecycle stage identification.

ChurnPredictorService

Churn risk scoring based on rental frequency decay, gap analysis, and re-engagement recommendations.

ParentalControlService

Age-based content filtering, parental profiles, rating restrictions, and viewing history controls.

🔍 Discovery & Content

RecommendationService

Content-based and collaborative filtering recommendations using genre preferences, rental history, and similar-user patterns.

MovieSimilarityService

Computes similarity scores between movies based on genre, rating, release date, and co-rental patterns.

MovieInsightsService

Deep analytics per movie: rental velocity, revenue trends, audience demographics, and performance comparisons.

MovieLifecycleService

Tracks movies through lifecycle stages (New Release → Popular → Catalog → Archive) with automated transitions.

CollectionService

Curated movie collections (staff picks, seasonal, thematic) with ordering and display management.

TaggingService

User-defined and system tags for movies, tag-based search, and tag cloud generation.

ReviewService

Customer reviews with ratings, helpfulness voting, moderation, and aggregate score computation.

WatchlistService

Personal watchlists with priority ordering, availability notifications, and sharing.

MovieNightPlannerService

Plan movie nights with group preferences, schedule coordination, and snack suggestions.

FranchiseTrackerService

Track movie franchises (series, sequels, prequels) with watch-order recommendations and completion tracking.

MovieComparisonService

Side-by-side movie comparison on ratings, revenue, rental count, and audience overlap.

💰 Commerce & Promotions

CouponService

Coupon creation, validation, redemption with percentage/fixed discounts, expiry, and usage limits.

GiftCardService

Gift card issuance, balance management, partial redemption, and transfer between customers.

BundleService

Movie bundles (rent 3 for price of 2), bundle creation, pricing rules, and availability checks.

SeasonalPromotionService

Time-bound promotions tied to seasons/holidays with automatic activation and genre-specific discounts.

DisputeResolutionService

Customer dispute filing, investigation workflows, resolution tracking, and refund processing.

📊 Analytics & Operations

RentalForecastService

Demand forecasting using historical patterns, seasonal adjustments, and trend analysis.

RevenueAnalyticsService

Revenue reporting by period, genre, tier, and trend. Includes linear regression forecasting with confidence intervals.

RatingEngineService

Aggregate rating computation with statistical analysis (mean, median, standard deviation, distribution).

DashboardService

Single-pass dashboard aggregation: top movies, top customers, genre revenue, membership breakdown, recent rentals, and monthly revenue — all in O(R).

StaffSchedulingService

Employee shift scheduling, availability management, conflict detection, and coverage optimization.

StaffPerformanceService

Staff performance metrics, KPI tracking, peer comparison, and review period analytics.

StoreEventService

In-store event planning (movie nights, premieres), RSVPs, capacity management, and calendar integration.

ReferralService

Customer referral program with tracking codes, reward attribution, and conversion analytics.

NotificationService

Customer notification management for due dates, availability, promotions, and account updates.

API Reference

Detailed method signatures and return types for key services. For complete API documentation, see SERVICES.md.

PricingService

MethodReturnsDescription
GetMovieDailyRate(movie)decimalBase daily rate: new releases $5.99, catalog $2.99, per-movie overrides
GetBenefits(tier)MembershipBenefitsTier benefits: discount %, extended days, max concurrent rentals

RentalReturnService

MethodReturnsDescription
ProcessReturn(rentalId, condition, returnDate)ReturnReceiptFull return workflow with late fees, damage charges, loyalty points
ProcessBatchReturn(ids, condition, returnDate)BatchReturnResultBatch return with individual receipts and error tracking
CalculateLateFee(dueDate, returnDate, dailyRate, tier)ReturnLateFeeBreakdownLate fee with grace period, tier discount, and cap
GetOverdueRentals()List<OverdueRentalInfo>All overdue rentals with projected fees and recommended actions
GetCustomerReturnProfile(customerId)CustomerReturnProfileReturn history: on-time rate, late fees paid, reliability rating
EstimateCurrentLateFee(rentalId)LateFeeEstimateSelf-service “what would I owe?” projection

DashboardService

MethodReturnsDescription
GetDashboard()DashboardDataComplete dashboard: stats, top movies/customers, genre revenue, membership breakdown, recent rentals, monthly revenue

Internally uses AggregateSinglePass() to compute all metrics in a single O(R) pass over rentals, replacing 6 separate iterations.

ChurnPredictorService

MethodReturnsDescription
PredictChurn(customerId)ChurnPredictionChurn risk score (0–1) with contributing factors
GetAtRiskCustomers(threshold)List<ChurnPrediction>All customers above churn-risk threshold

RecommendationService

MethodReturnsDescription
GetRecommendations(customerId, count)List<MovieRecommendation>Personalized movie recommendations
GetSimilarMovies(movieId, count)List<MovieRecommendation>Movies similar to a given title