JavaRush /Java блогу /Random-KY /Сервлеттерди жана jspди колдонуу менен жөнөкөй веб-тиркем...
Стас Пасинков
Деңгээл
Киев

Сервлеттерди жана jspди колдонуу менен жөнөкөй веб-тиркеме түзүү (1-бөлүк)

Группада жарыяланган
Макаланы түшүнүү үчүн талап кылынган бorм деңгээли: сиз Java Core программасын аздыр-көптүр түшүндүңүз жана JavaEE технологияларын жана веб-программалоону карагыңыз келет. Эгер сиз учурда макалага жакын темаларды камтыган Java Collections квестин окуп жатсаңыз, бул абдан маанилүү. Сервлеттерди жана jspди колдонуу менен жөнөкөй веб-тиркеме түзүү (1-бөлүк) - 1Бул материал менин макаламдын логикалык уландысы болуп саналат IntelliJ Idea Enterprise ичинде жөнөкөй веб-долбоорду түзүү . Анда мен жумушчу веб-долбоордун шаблонун кантип түзүүнү көрсөттүм. Бул жолу мен сизге Java Servlet API жана JavaServer Pages API технологияларын колдонуу менен жөнөкөй, бирок кооз веб тиркемесин кантип түзүүнү көрсөтөм. Биздин колдонмо эки шилтемеси бар үй баракчасына ээ болот:
  • колдонуучу кошуу барагына;
  • колдонуучу тизмесин көрүү барагына.
Мен дагы эле IntelliJ Idea Enterprise Edition, Apache Maven (бир нече көз карандылыкты камтышы) жана Apache Tomcat колдоном. Аягында, биз W3.CSS алкагын колдонуп, тиркемени "кооздойбуз" . Учурда сизде бош долбоор бар деп ойлойбуз, аны биз бул жерде иштеп чыгабыз. Болбосо, биринчи макаланы карап чыгып, аны жасаңыз. Бул бир нече мүнөттү талап кылат :)

Келечектеги колдонмонун түзүмү жөнүндө бир аз

Биздин башкы бет ( / ) баш жана эки шилтеме/баскычтары бар эң жөнөкөй статикалык html баракчасы болот:
  • жаңы колдонуучуну кошуу ( /add дарегине жөнөтүлөт );
  • колдонуучулардын тизмесин көрүү ( /list ге жөнөтөт ).
Tomcat бул даректерге суроо-талаптарды кармап, аларды биз жасай турган эки сервлеттин бирине жөнөтөт (карталоону web.xml файлында сүрөттөп беребиз ). Ал эми сервлеттер, өз кезегинде, суроо-талаптарды иштеп чыгат, маалыматтарды даярдайт (же колдонуучу кошулса, сактайт) жана башкарууну тиешелүү jsp файлдарына өткөрүп берет, алар натыйжаны мурунтан эле "көрсөтөт". Биз маалыматтарды эң кеңири таралган тизмеде (Тизмеде) сактайбыз.

Статикалык үй баракчасын түзөлү

Веб папкаңызда index.jsp бар болсо , аны жок кылыңыз. Анын ордуна, бул папкада биз index.html деп аталган жөнөкөй html файлын түзөбүз :
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>My super project!</title>
</head>
<body>
    <!-- header -->
    <div>
        <h1>Super app!<//h1>
    </div>

    <div>       <!-- content -->
        <div>    <!-- buttons holder -->
            <button onclick="location.href='/list'">List users<//button>
            <button onclick="location.href='/add'">Add user<//button>
        </div>
    </div>
</body>
</html>
Бул жерде татаал эч нерсе жок. Аталышында биз баракчабыздын аталышын көрсөтөбүз. Барактын негизги бөлүгүндө бизде эки негизги div бар: баш (баш) жана мазмун (мазмун). Мазмунда биздин баскычтар үчүн кармагыч бар жана чындыгында эки баскыч басылганда, тиешелүү даректерге жөнөтүлөт. Долбоорду иштетип, анын азыр кандай экенин көрө аласыз. Эгер баскычтарды чыкылдатсаңыз, 404 катасы бар барактар ​​ачылат, анткени алар бизде азырынча жок. Бирок бул баскычтар иштешин көрсөтүп турат. Бул эң универсалдуу вариант эмес экенин белгилей кетейин, анткени сизде күтүлбөгөн жерден JavaScript өчүрүлгөн болсо, бул баскычтар браузерде эч кандай пайдасыз болуп калат. Бирок биз эч ким JavaScriptти өчүргөн эмес деп ойлойбуз :). Жөнөкөй шилтемелерди колдонсо болот экен, бирок мен баскычтарды жактырам. Сиз эң жакшы көргөн нерсени кыласыз. Менин мисалдарымда divs көп болот деп карабаңыз . Ошондо биз аларды стилдер менен толтурабыз, жана баары сулуураак көрүнөт :).

Натыйжаны көрсөтүү үчүн jsp файлдарын түзүңүз

Ошол эле веб каталогдо биз jsp файлдарыбызды сала турган папканы түзөбүз . Мен аны көрүүлөр деп атадым, дагы бир жолу импровизация кыла аласыз. Бул папкада биз эки jsp файлын түзөбүз:
  • add.jsp — колдонуучуларды кошуу барагы;
  • list.jsp - колдонуучулардын тизмесин көрсөтүү үчүн бет.
Келгиле, аларга ылайыктуу бет баштарын берели. "Жаңы колдонуучуну кошуу" жана "Колдонуучулар тизмеси" сыяктуу бир нерсе жана биз аны азырынча ошол бойдон калтырабыз.

Келгиле, эки сервлет түзөлү

Сервлеттер Tomcat аларга өткөрө турган суроо-талаптарды кабыл алып, иштетишет. src/main/java папкасында биздин булактарды камтыган колдонмо пакетин түзөбүз. Ал жерде бизде дагы ар түрдүү пакеттер болот. Ошондуктан, бул пакеттер бири-биринин ичинде түзүлбөшү үчүн, келгиле, колдонмо пакетинде кандайдыр бир класс түзөлү (андан кийин аны жок кылабыз). Эми колдонмо пакетинде үч түрдүү пакетти түзөлү :
  • an objectтер - бул жерде биздин субъекттер (колдонуучу an objectтерин сүрөттөгөн класстын өзү) болот;
  • модель - биздин модель бул жерде болот (бул жөнүндө бир аздан кийин көбүрөөк);
  • сервлеттер - бул жерде биздин сервлеттер болот.
Андан кийин, сиз ошол классты колдонмо топтомунан коопсуз алып салсаңыз болот (эгер сиз аны түзсөңүз, албетте). Сервлет пакетинде биз эки класс түзөбүз:
  • AddServlet - /add дарегинде алынган суроо-талаптарды иштетет ;
  • ListServlet - /list боюнча алынган суроо-талаптарды иштетет .

Mavenдеги көз карандылыкты туташтыруу

Tomcat versionсы 9.* Servlet versionсы 4.0 жана JavaServer Pages versionсы 2.3 спецификацияларын ишке ашырат. Бул Tomcat 9 расмий documentациясында экинчи саптын биринчи абзацында жазылган. Бул, эгерде сиз мага окшоп, Tomcatтын ушул versionсын колдонуп жатсаңыз, анда биз жазып жана иштетүү үчүн жөнөткөн code так көрсөтүлгөн versionларды колдонот дегенди билдирет. Бирок биз бул спецификацияларды биздин долбоордо болушун каалайбыз, ошондуктан аларды колдонгон codeубуз жок дегенде ийгorктүү компиляциялансын. Бул үчүн биз аларды биздин долбоорго жүктөшүбүз керек. Бул жерде Мавен жардамга келет.

Жалпы эреже бул: Maven аркылуу долбооруңузга бир нерсе туташтырсаңыз:

  • Maven репозиторийинин веб-сайтына өтүңүз;
  • керектүү китепкананы жана сизге керектүү versionны издеңиз;
  • сиз pom.xml'иңизге киргизүү керек болгон көз карандылык codeун аласыз;
  • киргизүү! :)
Ошентип, баштайлы. Биринчиден, пом файлын даярдайлы . /versionдан кийин , бирок /project ге чейин , төмөнкүнү киргизиңиз:
<dependencies>

</dependencies>
Ошентип, биз бул тегдердин ичинде бизге керектүү көз карандылыктарды тизмектей турганыбызды айттык. Эми mvnrepository.com сайтына өтүңүз , жогору жакта издөө талаасы болот. Биринчиден, издөөгө сервлетти киргизиңиз. Биринчи натыйжа, жети миңден ашык колдонуу бар, бизге ылайыктуу. Бизге 4.0 versionсы керек экенин унутпайбыз (Tomcat 9 үчүн; башка versionлар үчүн эски ишке ашыруулар ылайыктуу болушу мүмкүн). Бул абдан жаңы version, ошондуктан көп колдонулbyte, бирок бул бизге керек. Ар кандай пакет менеджерлери үчүн бул көз карандылыктын codeун ала турган барак ачылат жана сиз аны жөн эле жүктөп алсаңыз болот. Бирок биз аны Maven аркылуу туташтыргыбыз келгендиктен, биз Maven өтмөгүндөгү codeду тандайбыз. Биз көчүрүп алып, көз карандылыктар бөлүмүндөгү pom файлыбызга чаптайбыз. Эгер IDEAнын төмөнкү оң бурчунда авто-импортту иштетүүнү каалайбызбы деген билдирме пайда болсо, биз макулбуз. Эгер сиз кокустан баш тартсаңыз, "Орнотууларга" өтүп, авто-импортту кол менен иштетиңиз: Орнотуулар (Ctrl + Alt + S) -> Куруу, Аткаруу, Жайгаштыруу -> Maven -> Импорттоо Бул үчүн pom файлы жана IDEA конфигурация файлдары сакталат. долбоор синхрондоштуруу. Эми ошол эле принципти колдонуп, биз JavaServer Pages 2.3 versionсын табабыз жана туташтырабыз (издөөдө jsp киргизиңиз). Биз Mavenди кабыл алгандыктан, дароо биздин булактар ​​Java 8 синтаксисине туура келерин жана аларды ошол эле versionнын byte codeуна компиляциялоо керектигин айталы. Бардык бул манипуляциялардан кийин, биздин pom.xml төмөнкүдөй көрүнөт:
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>ru.javarush.info.fatfaggy</groupId>
    <artifactId>my-super-project</artifactId>
    <version>1.0-SNAPSHOT</version>

    <properties>
        <maven.compiler.source>1.8</maven.compile.source>
        <maven.compiler.target>1.8</maven.compile.target>
    </properties>

    <dependencies>
        <!-- Servlet API 4.0 for tomcat 9 -->
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>javax.servlet-api</artifactId>
            <version>4.0.0</version>
            <scope>provided</scope>
        </dependency>

        <!-- JavaServer Pages API 2.3 for tomcat 9 -->
        <dependency>
            <groupId>javax.servlet.jsp</groupId>
            <artifactId>javax.servlet.jsp-api</artifactId>
            <version>2.3.1</version>
            <scope>provided</scope>
        </dependency>
    </dependencies>

</project>

Биздин сервлеттерди чыныгы сервлет кылуу

Бул учурда, биз түзгөн сервлеттердин бир нечеси чындыгында кадимки класстар. Алардын эч кандай функциясы жок. Бирок азыр биз Servlet APIди биздин долбоорго туташтырдык, эгер ошондой болсо, биз ошол жерден класстарды колдоно алабыз. Сервлеттерибизди "чыныгы" сервлет кылуу үчүн, аларды HttpServlet классынан мурастап алышыбыз керек .

Карталоо же бөлүү

Эми кандайдыр бир жол менен Tomcatга айтып койсоңуз жакшы болмок, ошондо /кошуудан келген суроо-талаптар биздин AddServlet сервлети тарабынан каралат , демек, /тизмден келген суроо-талаптар ListServlet сервлети тарабынан чечилет . Бул процесс карта түзүү деп аталат . Бул web.xml файлында ушул принципке ылайык жасалат :
  • адегенде биз сервлетти сүрөттөйбүз (биз кандайдыр бир ат берип, класстын өзүнө жол көрсөтөбүз);
  • анда биз бул сервлетти белгилүү бир дарекке байлайбыз (биз ага жаңы эле берген сервлеттин атын көрсөтөбүз жана бул сервлетке суроо-талаптар жөнөтүлүшү керек болгон даректи көрсөтөбүз).
Сервлетти сүрөттөп көрөлү:
<servlet>
    <servlet-name>add</servlet-name>
    <servlet-class>app.servlets.AddServlet</servlet-class>
</servlet>
Эми биз аны дарекке байлайбыз:
<servlet-mapping>
    <servlet-name>add</servlet-name>
    <url-pattern>/add</url-pattern>
</servlet-mapping>
Көрүнүп тургандай, сервлеттин аты эки учурда бирдей. Ушунун аркасында, Tomcat эгер өтүнүч /add дарегине келсе, аны app.servlets.AddServlet сервлетине өткөрүп берүү керек экенин билет . Экинчи сервлет менен да ушундай кылабыз. Натыйжада, биздин web.xml болжол менен төмөнкү мазмунга ээ:
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
         version="3.1">

    <!-- add servlet -->
    <servlet>
        <servlet-name>add</servlet-name>
        <servlet-class>app.servlets.AddServlet</servlet-class>
    </servlet>

    <servlet-mapping>
        <servlet-name>add</servlet-name>
        <url-pattern>/add</url-pattern>
    </servlet-mapping>

    <!-- list servlet -->
    <servlet>
        <servlet-name>list</servlet-name>
        <servlet-class>app.servlets.ListServlet</servlet-class>
    </servlet>

    <servlet-mapping>
        <servlet-name>list</servlet-name>
        <url-pattern>/list</url-pattern>
    </servlet-mapping>
</web-app>
Баса, биз бул жерде ( / боюнча ) негизги бет үчүн белги түзгөн жокпуз. Чындыгында, бул учурда бизге кереги жок. Биздин үй баракчабыз эки баскычты көрсөткөн жөнөкөй html файлы . Динамикалык мазмун жок, ошондуктан биз үчүн өзүнчө сервлет түзүүнүн мааниси жок, ага / дарегинен суроо-талаптар жөнөтүлөт жана кээ бир jspге өткөрүүдөн башка эч нерсе кылbyte (ал дагы болушу керек). түзүлгөн), ал тартылмак Эгерде бизде эки баскыч болгондо. Бизге мунун кереги жок; биз статикалык ресурска ыраазыбыз. Tomcat суроо-талапты алганда, мындай даректе суроону иштете ала турган бир дагы сервлет жок экенин текшерет, андан кийин бул даректе чындыгында даяр html файлы бар экенин көрөт, аны ийгorктүү жөнөтөт. . Биз тиркемени кайра иштете алабыз (serverди өчүрүп күйгүзүңүз же сиз каалагандай кайра жайгаштырыңыз) жана негизги беттин көрсөтүлгөнүн, эч нерсе бузулбаганын, баскычтарды чыкылдатканда, өтүүлөр болуп жатканын текшерип, бирок азыр ката да бар. жазылган. Айтмакчы, эгерде мурда бизде 404 катасы болсо, азыр бизде 405. Бул карталоо иштеди, сервлеттер табылды, бирок аларда өтүнүчтү иштетүү үчүн эч кандай ылайыктуу ыкмалар жок. Эгерде бул этапта сиз дагы эле 404 катасын алып жатсаңыз, баары туура жасалган болсо да, балким, сиз идеядагы жайылтуу конфигурациясын тууралашыңыз керек. Бул үчүн, сиз конфигурацияларды түзөтүүгө (баштоо баскычынын жанында) өтүшүңүз керек, терезенин оң жагындагы Жайгаштыруу өтмөгүнө өтүп, Колдонмо контекстинде ал жөн гана көрсөтүлгөнүн текшериңиз /

Кыскача лирикалык чегинүү: "капоттун астында" эмне болуп жатат?

Биздин тиркеме Tomcat'та кандай иштээри жөнүндө ойлонуп көргөнсүзбү? Ал жакта эмне болуп жатат? Жана негизги() ыкмасы кайда ? Браузериңизге localhost:8080 деп терип , бул дарекке барарыңыз менен, браузер http протоколу аркылуу бул дарекке суроо-талап жөнөтөт . Сурамдардын ар кандай "түрлөрү" болушу мүмкүн экенин билесиз деп үмүттөнөм, алардын эң популярдуусу GET жана POST . Ар бир суроого жооп болушу керек. GET өтүнүчү жооп катары ага даяр html codeу берилет деп күтөт , ал браузерге кайтарылат жана браузер бул codeду ар кандай тамгалар, баскычтар жана формалар менен сонун алмаштырат. POST суроо-талабы бир аз кызыктуураак, анткени ал өзү менен кошо кээ бир маалыматты камтыйт. Мисалы, колдонуучуну каттоо же авторизация формасында сиз маалыматыңызды киргиздиңиз жана "жөнөтүү" баскычын басыңыз. Ушул тапта сиздин жеке маалыматыңыз менен serverге POST сурамы жөнөтүлдү. Сервер бул маалыматты кабыл алып, аны иштетип, кандайдыр бир жооп кайтарды (мисалы, сиздин профorңиз менен html баракчасы ). Алардын ортосундагы негизги айырма GET суроо-талаптары serverден маалыматтарды алуу үчүн гана арналган, ал эми POST суроо-талаптары алар менен кээ бир маалыматты алып жүрөт жана serverдеги маалыматтар өзгөрүшү мүмкүн (мисалы, сиз сүрөтүңүздү serverге жүктөгөндө, ал POST сурамында учат жана server аны маалымат базасына кошот, башкача айтканда, кандайдыр бир өзгөрүү болот. Эми Tomcat'ка кайтайлы. Ал кардардан кандайдыр бир суроо-талапты алганда, ал даректи карайт. Өзүнүн маалыматтарын издейт ушундай дарекке суроо-талаптарды иштете турган ылайыктуу сервлет бар-жогун караңыз (же дароо кайтарыла турган даяр ресурс). Эгер ал кайтара турган эч нерсе таппаса, анда ал html баракчасы менен эмес, 404 жообу менен.Эгер ал ушул даректе "отурулган" ылайыктуу сервлетти тапса, ал сурамдын кандай түрүн кабыл алганын (GET, POST же башка) карап, андан кийин сервлеттен анын ыкмасы бар-жогун сурайт. Эгерде сервлет бул түрүн иштете алbyte десе, Tomcat кардарга 405 codeу менен жооп берет. Бул биз менен болгон окуя. Бирок ылайыктуу сервлет табылып, анын ылайыктуу ыкмасы болсо, Tomcat бул сервлеттин an objectин түзүп, аны жаңы жипте ( жип ) иштетет, бул сервлет өзүнчө жипте иштөөгө мүмкүндүк берет жана Tomcat андан ары ишин улантат. өз алдынча, суроо-талаптарды кабыл алуу жана жөнөтүү. Мындан тышкары, Tomcat дагы эки an objectти түзөт: бири HttpServletRequest түрү (мен кыскача келечекте сурам деп атайм), экинчиси HttpServletResponse түрү(Мен муну жооп деп атайм). Биринчи an objectте ал кардардын суроо-талабында кабыл алынган бардык маалыматтарды жайгаштырат, ошондуктан бул маалыматтардын бардыгын бул an objectтен чыгарып алса болот. Мунун бардыгынан кийин, ал бул эки an objectти өзүнчө жипте иштеп жаткан сервлеттин тиешелүү ыкмасына өткөрүп берет. Сервлет өз ишин бүтүрүп, кардарга жөнөтүүгө даяр жообу болоор замат, ал Томкатка желекти көтөрүп, "Бүттүм, баары даяр" деп айтат. Tomcat жоопту кабыл алып, кардарга жөнөтөт. Бул Tomcatга суроо-талаптарды кабыл алууга жана жоопторду үзгүлтүксүз жөнөтүүгө мүмкүндүк берет, ал эми бардык жумуштар өзүнчө жиптерде иштеген сервлеттер тарабынан аткарылат. Демек, биз сервлет codeун жазганда, аткарыла турган ишти аныктайбыз. Ооба, сиз main() ыкмасын Tomcatтин өзүндө деп ойлосоңуз болот (ооба, ал Java тorнде жазылган) жана биз Tomcatти "баштаганда" main().

Биз GET ыкмаларын сервлеттер менен кармап, жөнөкөй жоопторду жөнөтөбүз

Учурда биздин сервлеттерде ылайыктуу методдор (GET) жок, андыктан Tomcat бизге 405 катасын кайтарат. Келгиле, аларды жасайлы! HttpServlet классы , андан биз биздин сервлеттерди мурастап, ар кандай ыкмаларды аныктайт . Методдор үчүн кандайдыр бир code коюу үчүн, биз аларды жөн гана жокко чыгарабыз. Бул учурда, эки сервлеттеги doGet() ыкмасын жокко чыгарышыбыз керек .
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {

}
Көрүнүп тургандай, бул ыкма эки an objectти кабыл алат: req (суроо) жана жооп (жооп). Бул Tomcat бул сервлеттеги тиешелүү ыкманы чакырганда биз үчүн түзүп, толтурган an objectилер. Биринчиден, эң жөнөкөй жоопторду жасайлы. Бул үчүн, resp an objectин алып , андан жоопторду түзүү үчүн колдонула турган PrintWriter an objectин алыңыз. Ооба, аны колдонуу менен биз жөнөкөй сапты басып чыгарабыз.
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    PrintWriter writer = resp.getWriter();
    writer.println("Method GET from AddServlet");
}
ListServlet сервлетинде окшош нерсени жасайбыз , андан кийин serverибизди кайра ишке киргизебиз. Көрүнүп тургандай, баары иштейт! Баскычтарды басканда, биз PrintWriter менен "жазган" текст менен барактар ​​ачылат . Жөн гана жооптору бар баракчаларды түзүү үчүн даярдаган биздин jsp эч кандай колдонулbyte. Себеби өлүм жазасы аларга жетпейт. Серверлеттин өзү азыр жоопту жаратып, ишин бүтүрүп, Tomcatка кардарга жооп даяр экендигин билдирет. Tomcat жөн гана бул жоопту кабыл алып, кайра кардарга жөнөтөт. Биз башкарууну сервлеттерден jspге өткөрүп беребиз . Келгиле, методдорубуздун codeун мындайча өзгөртөлү:
  • биз суроо-талап an objectинен суроо-башкаруучу an objectин алабыз, анда биз башкарууну өткөргүбүз келген барактын jsp дарегин өткөрөбүз;
  • алынган an objectти колдонуп, биз башкарууну көрсөтүлгөн jsp барагына өткөрүп беребиз жана ал жерге Tomcatтан алган суроо-талап жана жооп an objectтерин тиркөөнү унутпаңыз.
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    RequestDispatcher requestDispatcher = req.getRequestDispatcher("views/add.jsp");
    requestDispatcher.forward(req, resp);
}
jsp барактарынын корпусунда (корпуска тегинин ичинде) биз кайсы беттин көрсөтүлүп жатканын так көрүү үчүн бир нерсе жаза алабыз. Андан кийин биз serverди кайра иштетип, текшеребиз. Негизги беттеги баскычтар басылып, барактар ​​ачылат, бул суроо-талаптар сервлеттерге жөнөтүлөт, андан кийин башкаруу мурунтан эле көрсөтүлгөн jsp баракчаларына өткөрүлүп берилет. Баары болду. Макаланын кийинки бөлүгүндө биз колдонмобуздун функционалдуулугу менен алектенебиз.

Дагы эмнени окуу керек:

IntelliJ Idea Enterprise ичинде жөнөкөй веб-долбоорду түзүү. Кадам-кадам, сүрөттөр менен


Менин чатым
Комментарийлер
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION