50 votes

Peut-on créer des vues sql / des procédures stockées en utilisant Entity Framework 4.1 Code first approach ?

Entity Framework 4.1 Code First fonctionne très bien pour créer des tables et des relations. Est-il possible de créer des vues sql ou des procédures stockées en utilisant l'approche Code first ? Toute indication à ce sujet sera très appréciée. Merci beaucoup !

2voto

Natas0007 Points 6

Le design d'emp fonctionne comme un champion ! J'utilise son modèle mais je mappe également les procédures stockées à l'intérieur de ma classe DbContext, ce qui permet d'appeler simplement ces méthodes de contexte au lieu d'utiliser SqlQuery() et d'appeler les procédures directement depuis mon référentiel. Comme les choses peuvent devenir un peu compliquées lorsque l'application se développe, j'ai créé une vérification dans ma méthode Seed qui s'assure que le nombre réel de paramètres de la procédure stockée correspond au nombre de paramètres de la méthode de mappage. J'ai également mis à jour la boucle DROP mentionnée par l'empereur. Au lieu de devoir maintenir un dossier/fichier séparé pour les déclarations DROP, je lis simplement la première ligne de chaque fichier sql et je remplace CREATE con DROP (assurez-vous que la première ligne est toujours juste CREATE PROCEDURE ProcName ). De cette façon, toutes les procédures de mon dossier StoredProcs sont supprimées et recréées à chaque fois que Update-Database est exécuté. L'abandon est également enveloppé dans un bloc try-catch au cas où la procédure serait nouvelle. Pour que le comptage des paramètres de la procédure fonctionne, vous devez vous assurer que le bloc try-catch est entouré d'un bloc BEGIN/END autour de votre tsql puisque chaque ligne du fichier est lue jusqu'à BEGIN. Assurez-vous également que chaque paramètre sp est sur une nouvelle ligne.

        // Drop Stored Procs
        foreach (var file in Directory.GetFiles(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "..\\DataContext\\SiteMigrations\\StoredProcs"), "*.sql"))
        {
            // Try to drop proc if its already created
            // Without this, for new procs, seed method fail on trying to delete
            try
            {
                StreamReader reader = new StreamReader(file);
                // Read first line of file to create drop command (turning CREATE [dbo].[TheProc] into DROP [dbo].[TheProc])
                string dropCommand = reader.ReadLine().Replace("CREATE", "DROP");

                context.Database.ExecuteSqlCommand(dropCommand, new object[0]);
            }
            catch { }

        }

        // Add Stored Procs
        foreach (var file in Directory.GetFiles(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "..\\DataContext\\SiteMigrations\\StoredProcs"), "*.sql"))
        {
            // File/Proc names must match method mapping names in DbContext
            int lastSlash = file.LastIndexOf('\\');
            string fileName = file.Substring(lastSlash + 1);
            string procName = fileName.Substring(0, fileName.LastIndexOf('.'));

            // First make sure proc mapping in DbContext contain matching parameters.  If not throw exception.
            // Get parameters for matching mapping
            MethodInfo mi = typeof(SiteContext).GetMethod(procName);

            if (mi == null)
            {
                throw new Exception(String.Format("Stored proc mapping for {0} missing in DBContext", procName));
            }

            ParameterInfo[] methodParams = mi.GetParameters();
            // Finished getting parameters

            // Get parameters from stored proc
            int spParamCount = 0;
            using (StreamReader reader = new StreamReader(file))
            {
                string line;                    
                while ((line = reader.ReadLine()) != null) 
                {
                    // If end of parameter section, break out
                    if (line.ToUpper() == "BEGIN")
                    {
                        break;
                    }
                    else
                    {
                        if (line.Contains("@"))
                        {
                            spParamCount++;
                        }
                    }                        
                }
            }
            // Finished get parameters from stored proc

            if (methodParams.Count() != spParamCount)
            {
                string err = String.Format("Stored proc mapping for {0} in DBContext exists but has {1} parameter(s)" +
                    " The stored procedure {0} has {2} parameter(s)", procName, methodParams.Count().ToString(), spParamCount.ToString());
                throw new Exception(err);
            }
            else
            {
                context.Database.ExecuteSqlCommand(File.ReadAllText(file), new object[0]);
            }
        }

Profitez-en !

1voto

Comme Ladislav l'a souligné, DbContext en général, tend à minimiser la logique dans la base de données, mais il est possible d'exécuter un SQL personnalisé en utilisant la fonction context.Database.ExecuteSqlCommand() o context.Database.SqlQuery() .

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X