10/38 PLS-00201: 'ID' must be declared
Du väljer data till en lokal variabel ID
som inte har deklarerats. Om du vill deklarera en lokal variabel, gör du det i deklarationsavsnittet mellan AS
och BEGIN
PROCEDURE create_emp(p_last_name IN employees.last_name%type,
p_first_name IN employees.first_name%type,
p_email IN employees.email%type,
p_hire_date IN employees.hire_date%type,
p_job_id IN employees.job_id%type)
AS
id integer;
BEGIN
SELECT emp_sequence.NEXTVAL INTO id FROM dual;
Om du ska göra det, skulle du vilja använda den lokala variabeln id
i din INSERT
uttalande istället för att anropa emp_sequence.nextval
direkt. Personligen skulle jag dock bli av med den lokala variabeln, bli av med den initiala SELECT
, och gör bara emp_sequence.nextval
ring in din INSERT
påstående.
11/17 PL/SQL: ORA-00913: too many values
Oavsett hur du gör det skulle du dock behöva antalet kolumner i din INSERT
för att matcha antalet VALUES
du anger.
PROCEDURE create_emp(p_last_name IN employees.last_name%type,
p_first_name IN employees.first_name%type,
p_email IN employees.email%type,
p_hire_date IN employees.hire_date%type,
p_job_id IN employees.job_id%type)
AS
id integer;
BEGIN
SELECT emp_sequence.NEXTVAL INTO id FROM dual;
INSERT INTO employees(employee_id, last_name, first_name, email, hire_date, job_id)
VALUES (id, p_last_name, p_first_name, p_email, p_hire_date, p_job_id);
END create_emp;
Eller om du vill anropa sekvensen direkt
PROCEDURE create_emp(p_last_name IN employees.last_name%type,
p_first_name IN employees.first_name%type,
p_email IN employees.email%type,
p_hire_date IN employees.hire_date%type,
p_job_id IN employees.job_id%type)
AS
BEGIN
INSERT INTO employees(employee_id, last_name, first_name, email, hire_date, job_id)
VALUES ( emp_sequence.NEXTVAL, p_last_name, p_first_name, p_email, p_hire_date, p_job_id);
END create_emp;
På samma sätt, för ditt nästa fel, bör antalet variabler som du hämtar till matcha antalet kolumner som du väljer
51/5 PL/SQL: ORA-00947: insufficient values
I din read_emp väljer du 7 saker och försöker lägga in dem i 6 variabler. Förutsatt att du inte vill returnera employee_id
, bry dig inte om att välja det.
PROCEDURE read_emp(p_employee_id IN employees.employee_id%type,
p_last_name OUT employees.last_name%type,
p_first_name OUT employees.first_name%type,
p_email OUT employees.email%type,
p_hire_date OUT employees.hire_date%type,
p_job_id OUT employees.job_id%type,
p_salary OUT employees.salary%type)
AS
BEGIN
SELECT last_name, first_name, email, hire_date, job_id, salary
INTO p_last_name, p_first_name, p_email, p_hire_date, p_job_id, p_salary
FROM EMPLOYEES
WHERE employee_id = p_employee_id;
END read_emp;
Medan du kan skriva en read_emp
procedur som denna, skulle det generellt vara mer meningsfullt att skapa en funktion som returnerar en employees%rowtype
spela in istället.
Dina undantagsklausuler bör tas bort. I bästa fall kasserar de felstacken som skulle berätta för en person vad som misslyckades och var. I värsta fall döljer de felen (du ska aldrig anta att någon någonsin kommer att se något som du skriver till dbms_output
) och får anropskoden att tro att någon operation lyckades när den inte gjorde det.